diff --git a/api/http/handler/endpoint.go b/api/http/handler/endpoint.go index 972f766cf..4b6a43220 100644 --- a/api/http/handler/endpoint.go +++ b/api/http/handler/endpoint.go @@ -68,13 +68,16 @@ type ( } putEndpointsRequest struct { - Name string `valid:"-"` - URL string `valid:"-"` - PublicURL string `valid:"-"` - GroupID int `valid:"-"` - TLS bool `valid:"-"` - TLSSkipVerify bool `valid:"-"` - TLSSkipClientVerify bool `valid:"-"` + Name string `valid:"-"` + URL string `valid:"-"` + PublicURL string `valid:"-"` + GroupID int `valid:"-"` + TLS bool `valid:"-"` + TLSSkipVerify bool `valid:"-"` + TLSSkipClientVerify bool `valid:"-"` + AzureApplicationID string `valid:"-"` + AzureTenantID string `valid:"-"` + AzureAuthenticationKey string `valid:"-"` } postEndpointPayload struct { @@ -143,7 +146,7 @@ func (handler *EndpointHandler) createAzureEndpoint(payload *postEndpointPayload endpoint := &portainer.Endpoint{ Name: payload.name, - URL: payload.url, + URL: proxy.AzureAPIBaseURL, Type: portainer.AzureEnvironment, GroupID: portainer.EndpointGroupID(payload.groupID), PublicURL: payload.publicURL, @@ -405,8 +408,6 @@ func (handler *EndpointHandler) handleGetEndpoint(w http.ResponseWriter, r *http return } - endpoint.AzureCredentials = portainer.AzureCredentials{} - encodeJSON(w, endpoint, handler.Logger) } @@ -518,6 +519,18 @@ func (handler *EndpointHandler) handlePutEndpoint(w http.ResponseWriter, r *http endpoint.GroupID = portainer.EndpointGroupID(req.GroupID) } + if endpoint.Type == portainer.AzureEnvironment { + if req.AzureApplicationID != "" { + endpoint.AzureCredentials.ApplicationID = req.AzureApplicationID + } + if req.AzureTenantID != "" { + endpoint.AzureCredentials.TenantID = req.AzureTenantID + } + if req.AzureAuthenticationKey != "" { + endpoint.AzureCredentials.AuthenticationKey = req.AzureAuthenticationKey + } + } + folder := strconv.Itoa(int(endpoint.ID)) if req.TLS { endpoint.TLSConfig.TLS = true diff --git a/api/http/proxy/factory.go b/api/http/proxy/factory.go index 70ba4543d..f3c43510f 100644 --- a/api/http/proxy/factory.go +++ b/api/http/proxy/factory.go @@ -10,7 +10,8 @@ import ( "github.com/portainer/portainer/crypto" ) -const azureAPIBaseURL = "https://management.azure.com" +// AzureAPIBaseURL is the URL where Azure API requests will be proxied. +const AzureAPIBaseURL = "https://management.azure.com" // proxyFactory is a factory to create reverse proxies to Docker endpoints type proxyFactory struct { @@ -28,7 +29,7 @@ func (factory *proxyFactory) newHTTPProxy(u *url.URL) http.Handler { } func newAzureProxy(credentials *portainer.AzureCredentials) (http.Handler, error) { - url, err := url.Parse(azureAPIBaseURL) + url, err := url.Parse(AzureAPIBaseURL) if err != nil { return nil, err } diff --git a/app/azure/components/azure-endpoint-config/azure-endpoint-config.js b/app/azure/components/azure-endpoint-config/azure-endpoint-config.js new file mode 100644 index 000000000..b5af18fb7 --- /dev/null +++ b/app/azure/components/azure-endpoint-config/azure-endpoint-config.js @@ -0,0 +1,8 @@ +angular.module('portainer.azure').component('azureEndpointConfig', { + bindings: { + applicationId: '=', + tenantId: '=', + authenticationKey: '=' + }, + templateUrl: 'app/azure/components/azure-endpoint-config/azureEndpointConfig.html' +}); diff --git a/app/azure/components/azure-endpoint-config/azureEndpointConfig.html b/app/azure/components/azure-endpoint-config/azureEndpointConfig.html new file mode 100644 index 000000000..c0d839102 --- /dev/null +++ b/app/azure/components/azure-endpoint-config/azureEndpointConfig.html @@ -0,0 +1,29 @@ +
+
+ Azure configuration +
+ +
+ +
+ +
+
+ + +
+ +
+ +
+
+ + +
+ +
+ +
+
+ +
diff --git a/app/portainer/components/datatables/endpoints-datatable/endpointsDatatable.html b/app/portainer/components/datatables/endpoints-datatable/endpointsDatatable.html index c22dfdc5e..b18084d6e 100644 --- a/app/portainer/components/datatables/endpoints-datatable/endpointsDatatable.html +++ b/app/portainer/components/datatables/endpoints-datatable/endpointsDatatable.html @@ -39,6 +39,13 @@ + + + Type + + + + URL @@ -66,6 +73,12 @@ {{ item.Name }} {{ item.Name }} + + + + {{ item.Type | endpointtypename }} + + {{ item.URL | stripprotocol }} {{ item.GroupName }} diff --git a/app/portainer/components/endpoint-selector/endpointSelector.html b/app/portainer/components/endpoint-selector/endpointSelector.html index eddbc3e55..79332e2b0 100644 --- a/app/portainer/components/endpoint-selector/endpointSelector.html +++ b/app/portainer/components/endpoint-selector/endpointSelector.html @@ -11,7 +11,7 @@ @@ -19,7 +19,7 @@ diff --git a/app/portainer/filters/filters.js b/app/portainer/filters/filters.js index a72ab82cc..bda52fe63 100644 --- a/app/portainer/filters/filters.js +++ b/app/portainer/filters/filters.js @@ -102,6 +102,28 @@ angular.module('portainer.app') return ''; }; }) +.filter('endpointtypename', function () { + 'use strict'; + return function (type) { + if (type === 1) { + return 'Docker'; + } else if (type === 2) { + return 'Agent'; + } else if (type === 3) { + return 'Azure ACI'; + } + return ''; + }; +}) +.filter('endpointtypeicon', function () { + 'use strict'; + return function (type) { + if (type === 3) { + return 'fab fa-microsoft'; + } + return 'fab fa-docker'; + }; +}) .filter('ownershipicon', function () { 'use strict'; return function (ownership) { diff --git a/app/portainer/services/api/endpointService.js b/app/portainer/services/api/endpointService.js index 9db9f4165..8f1eb5f4d 100644 --- a/app/portainer/services/api/endpointService.js +++ b/app/portainer/services/api/endpointService.js @@ -33,25 +33,12 @@ function EndpointServiceFactory($q, Endpoints, FileUploadService) { return Endpoints.updateAccess({id: id}, {authorizedUsers: authorizedUserIDs, authorizedTeams: authorizedTeamIDs}).$promise; }; - service.updateEndpoint = function(id, endpointParams) { - var query = { - name: endpointParams.name, - PublicURL: endpointParams.PublicURL, - GroupId: endpointParams.GroupId, - TLS: endpointParams.TLS, - TLSSkipVerify: endpointParams.TLSSkipVerify, - TLSSkipClientVerify: endpointParams.TLSSkipClientVerify, - authorizedUsers: endpointParams.authorizedUsers - }; - if (endpointParams.type && endpointParams.URL) { - query.URL = endpointParams.type === 'local' ? ('unix://' + endpointParams.URL) : ('tcp://' + endpointParams.URL); - } - + service.updateEndpoint = function(id, payload) { var deferred = $q.defer(); - FileUploadService.uploadTLSFilesForEndpoint(id, endpointParams.TLSCACert, endpointParams.TLSCert, endpointParams.TLSKey) + FileUploadService.uploadTLSFilesForEndpoint(id, payload.TLSCACert, payload.TLSCert, payload.TLSKey) .then(function success() { deferred.notify({upload: false}); - return Endpoints.update({id: id}, query).$promise; + return Endpoints.update({id: id}, payload).$promise; }) .then(function success(data) { deferred.resolve(data); diff --git a/app/portainer/views/endpoints/edit/endpoint.html b/app/portainer/views/endpoints/edit/endpoint.html index 54e75b445..a8ef8c7a4 100644 --- a/app/portainer/views/endpoints/edit/endpoint.html +++ b/app/portainer/views/endpoints/edit/endpoint.html @@ -28,12 +28,12 @@
- +
-
+
+
Grouping @@ -57,7 +62,7 @@
-
+
Security
diff --git a/app/portainer/views/endpoints/edit/endpointController.js b/app/portainer/views/endpoints/edit/endpointController.js index bdcbc63b0..1d7cd8c3d 100644 --- a/app/portainer/views/endpoints/edit/endpointController.js +++ b/app/portainer/views/endpoints/edit/endpointController.js @@ -23,22 +23,27 @@ function ($q, $scope, $state, $transition$, $filter, EndpointService, GroupServi var TLSSkipVerify = TLS && (TLSMode === 'tls_client_noca' || TLSMode === 'tls_only'); var TLSSkipClientVerify = TLS && (TLSMode === 'tls_ca' || TLSMode === 'tls_only'); - var endpointParams = { - name: endpoint.Name, - URL: endpoint.URL, + var payload = { + Name: endpoint.Name, PublicURL: endpoint.PublicURL, - GroupId: endpoint.GroupId, + GroupID: endpoint.GroupId, TLS: TLS, TLSSkipVerify: TLSSkipVerify, TLSSkipClientVerify: TLSSkipClientVerify, TLSCACert: TLSSkipVerify || securityData.TLSCACert === endpoint.TLSConfig.TLSCACert ? null : securityData.TLSCACert, TLSCert: TLSSkipClientVerify || securityData.TLSCert === endpoint.TLSConfig.TLSCert ? null : securityData.TLSCert, TLSKey: TLSSkipClientVerify || securityData.TLSKey === endpoint.TLSConfig.TLSKey ? null : securityData.TLSKey, - type: $scope.endpointType + AzureApplicationID: endpoint.AzureCredentials.ApplicationID, + AzureTenantID: endpoint.AzureCredentials.TenantID, + AzureAuthenticationKey: endpoint.AzureCredentials.AuthenticationKey }; + if ($scope.endpointType !== 'local' && endpoint.Type !== 3) { + payload.URL = 'tcp://' + endpoint.URL; + } + $scope.state.actionInProgress = true; - EndpointService.updateEndpoint(endpoint.Id, endpointParams) + EndpointService.updateEndpoint(endpoint.Id, payload) .then(function success(data) { Notifications.success('Endpoint updated', $scope.endpoint.Name); EndpointProvider.setEndpointPublicURL(endpoint.PublicURL);