-
Notifications
You must be signed in to change notification settings - Fork 10
Qa 7710 #25
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Qa 7710 #25
Changes from all commits
52e6834
162b33f
399bdcb
97d134c
08f3f09
82512d1
d48004e
2a3a5e7
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -4,9 +4,33 @@ import ( | |
"encoding/json" | ||
"errors" | ||
"github.com/qa-dev/jsonwire-grid/config" | ||
"time" | ||
"fmt" | ||
) | ||
|
||
type strategyParams struct { | ||
Namespace string | ||
PodCreationTimeout time.Duration | ||
} | ||
|
||
func (sp *strategyParams) UnmarshalJSON(b []byte) error { | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Выглядет так что тебе нужно добавить валидацию конфигов и тип There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. нужно координально все связанное с конфигами переделать, пока предлагаю оставить так как временное решение и вернуться к этому позже |
||
tempStruct := struct{ | ||
Namespace string `json:"namespace"` | ||
PodCreationTimeout string `json:"pod_creation_timeout"` | ||
} { | ||
"default", | ||
"1m", | ||
} | ||
if err := json.Unmarshal(b, &tempStruct); err != nil { | ||
return err | ||
} | ||
podCreationTimeout, err := time.ParseDuration(tempStruct.PodCreationTimeout) | ||
if err != nil { | ||
return fmt.Errorf("invalid value strategy.pod_creation_timeout in config, given: %v", tempStruct.PodCreationTimeout) | ||
} | ||
sp.Namespace = tempStruct.Namespace | ||
sp.PodCreationTimeout = podCreationTimeout | ||
return nil | ||
} | ||
|
||
type strategyConfig struct { | ||
|
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -9,20 +9,24 @@ import ( | |
"net" | ||
"strconv" | ||
"time" | ||
"strings" | ||
"fmt" | ||
) | ||
|
||
type kubernetesProviderInterface interface { | ||
Create(podName string, nodeParams nodeParams) error | ||
Create(podName string, nodeParams nodeParams) (nodeAddress string, err error) | ||
// idempotent operation | ||
Destroy(podName string) error | ||
} | ||
|
||
type kubernetesProvider struct { | ||
type kubDnsProvider struct { | ||
clientset *kubernetes.Clientset | ||
namespace string | ||
podCreationTimeout time.Duration | ||
clientFactory jsonwire.ClientFactoryInterface | ||
} | ||
|
||
func (p *kubernetesProvider) Create(podName string, nodeParams nodeParams) error { | ||
func (p *kubDnsProvider) Create(podName string, nodeParams nodeParams) (nodeAddress string, err error) { | ||
pod := &apiV1.Pod{} | ||
pod.ObjectMeta.Name = podName | ||
pod.ObjectMeta.Labels = map[string]string{"name": podName} | ||
|
@@ -32,62 +36,70 @@ func (p *kubernetesProvider) Create(podName string, nodeParams nodeParams) error | |
container.Image = nodeParams.Image | ||
port, err := strconv.Atoi(nodeParams.Port) | ||
if err != nil { | ||
return errors.New("convert to int nodeParams.Port, " + err.Error()) | ||
return "", errors.New("convert to int nodeParams.Port, " + err.Error()) | ||
} | ||
container.Ports = []apiV1.ContainerPort{{ContainerPort: int32(port)}} | ||
pod.Spec.Containers = append(pod.Spec.Containers, container) | ||
_, err = p.clientset.CoreV1Client.Pods(p.namespace).Create(pod) | ||
if err != nil { | ||
return errors.New("send command pod/create to k8s, " + err.Error()) | ||
return "", errors.New("send command pod/create to k8s, " + err.Error()) | ||
} | ||
|
||
service := &apiV1.Service{} | ||
service.ObjectMeta.Name = podName | ||
service.Spec.ClusterIP = "None" | ||
service.Spec.Ports = []apiV1.ServicePort{{Port: int32(port)}} | ||
service.Spec.Selector = map[string]string{"name": podName} | ||
_, err = p.clientset.CoreV1Client.Services(p.namespace).Create(service) | ||
if err != nil { | ||
return errors.New("send command service/create to k8s, " + err.Error()) | ||
stop := time.After(p.podCreationTimeout) | ||
log.Debugf("start waiting pod ip") | ||
var createdPodIP string | ||
LoopWaitIP: | ||
for { | ||
select { | ||
case <-stop: | ||
return "", fmt.Errorf("wait podIP stopped by timeout, %v", podName) | ||
default: | ||
time.Sleep(time.Second) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. А что будет если человек по не знанию поставит There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. в конфиг засовывать не стоит, так как это его лишь усложнит его There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Нет, он просто все время с таймаутом будет валиться, валидируй тогда значение на входе There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. возникает вопрос какой таймаут считать минимальным и нужно ли это? |
||
createdPod, err := p.clientset.CoreV1Client.Pods(p.namespace).Get(podName) | ||
if err != nil { | ||
log.Debugf("fail get created pod, %v, %v",podName, err) | ||
continue | ||
} | ||
if createdPod.Status.PodIP == "" { | ||
log.Debugf("empty pod ip, %v", podName) | ||
continue | ||
} | ||
createdPodIP = createdPod.Status.PodIP | ||
break LoopWaitIP | ||
} | ||
} | ||
|
||
// todo: пока так ожидаем поднятие ноды, так как не понятно что конкретно означают статусы возвращаемые через апи | ||
client := p.clientFactory.Create(net.JoinHostPort(podName, nodeParams.Port)) | ||
stop := time.After(40 * time.Second) | ||
log.Debugln("start waiting") | ||
Loop: | ||
nodeAddress = net.JoinHostPort(createdPodIP, nodeParams.Port) | ||
client := p.clientFactory.Create(nodeAddress) | ||
log.Debugln("start waiting selenium") | ||
LoopWaitSelenium: | ||
for { | ||
select { | ||
case <-stop: | ||
return errors.New("wait stopped by timeout") | ||
return "", fmt.Errorf("wait selenium stopped by timeout, %v", podName) | ||
default: | ||
time.Sleep(time.Second) | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. ВЫше описал. |
||
log.Debugln("start request") | ||
message, err := client.Health() | ||
if err != nil { | ||
log.Debugf("fail request, %v", err) | ||
continue | ||
} | ||
log.Debugf("done request, status: %v", message.Status) | ||
if message.Status == 0 { | ||
break Loop | ||
break LoopWaitSelenium | ||
} | ||
} | ||
} | ||
|
||
return nil | ||
return nodeAddress, nil | ||
} | ||
|
||
func (p *kubernetesProvider) Destroy(podName string) error { | ||
//Destroy - destroy all pod data (idempotent operation) | ||
func (p *kubDnsProvider) Destroy(podName string) error { | ||
err := p.clientset.CoreV1Client.Pods(p.namespace).Delete(podName, &apiV1.DeleteOptions{}) | ||
if err != nil { | ||
err = errors.New("send command pod/delete to k8s, " + err.Error()) | ||
return err | ||
} | ||
err = p.clientset.CoreV1Client.Services(p.namespace).Delete(podName, &apiV1.DeleteOptions{}) | ||
if err != nil { | ||
err = errors.New("send command service/delete to k8s, " + err.Error()) | ||
return err | ||
if err != nil && !strings.Contains(err.Error(), "not found") { | ||
return errors.New("send command pod/delete to k8s, " + err.Error()) | ||
} | ||
return nil | ||
} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
А за что отвечает ключ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
добавил комент в код
уникальный ключ, по которому мы понимаем как нам найти этот объект во внешнем мире + за то чтобы не добавить второй раз одно и то же
значение может зависеть от стратегии
для постоянных нод ip:port
для временных pod.name