Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
A
apollo
Project overview
Project overview
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
Administrator
apollo
Commits
b949afac
Commit
b949afac
authored
Sep 12, 2018
by
nobodyiam
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
allow public namespace created with no org prefix
parent
9e3aec54
Changes
7
Hide whitespace changes
Inline
Side-by-side
Showing
7 changed files
with
111 additions
and
22 deletions
+111
-22
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/controller/NamespaceController.java
...amework/apollo/portal/controller/NamespaceController.java
+6
-4
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/repository/AppNamespaceRepository.java
...work/apollo/portal/repository/AppNamespaceRepository.java
+1
-1
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/service/AppNamespaceService.java
.../framework/apollo/portal/service/AppNamespaceService.java
+50
-8
apollo-portal/src/main/resources/static/namespace.html
apollo-portal/src/main/resources/static/namespace.html
+20
-4
apollo-portal/src/main/resources/static/scripts/controller/NamespaceController.js
...esources/static/scripts/controller/NamespaceController.js
+4
-1
apollo-portal/src/main/resources/static/scripts/services/NamespaceService.js
...ain/resources/static/scripts/services/NamespaceService.js
+5
-4
apollo-portal/src/test/java/com/ctrip/framework/apollo/portal/service/AppNamespaceServiceTest.java
...mework/apollo/portal/service/AppNamespaceServiceTest.java
+25
-0
No files found.
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/controller/NamespaceController.java
View file @
b949afac
...
@@ -161,16 +161,18 @@ public class NamespaceController {
...
@@ -161,16 +161,18 @@ public class NamespaceController {
@PreAuthorize
(
value
=
"@permissionValidator.hasCreateAppNamespacePermission(#appId, #appNamespace)"
)
@PreAuthorize
(
value
=
"@permissionValidator.hasCreateAppNamespacePermission(#appId, #appNamespace)"
)
@RequestMapping
(
value
=
"/apps/{appId}/appnamespaces"
,
method
=
RequestMethod
.
POST
)
@RequestMapping
(
value
=
"/apps/{appId}/appnamespaces"
,
method
=
RequestMethod
.
POST
)
public
AppNamespace
createAppNamespace
(
@PathVariable
String
appId
,
@RequestBody
AppNamespace
appNamespace
)
{
public
AppNamespace
createAppNamespace
(
@PathVariable
String
appId
,
@RequestParam
(
defaultValue
=
"true"
)
boolean
appendNamespacePrefix
,
@RequestBody
AppNamespace
appNamespace
)
{
RequestPrecondition
.
checkArgumentsNotEmpty
(
appNamespace
.
getAppId
(),
appNamespace
.
getName
());
RequestPrecondition
.
checkArgumentsNotEmpty
(
appNamespace
.
getAppId
(),
appNamespace
.
getName
());
if
(!
InputValidator
.
isValidAppNamespace
(
appNamespace
.
getName
()))
{
if
(!
InputValidator
.
isValidAppNamespace
(
appNamespace
.
getName
()))
{
throw
new
BadRequestException
(
String
.
format
(
"Namespace格式错误: %s"
,
throw
new
BadRequestException
(
String
.
format
(
"Namespace格式错误: %s"
,
InputValidator
.
INVALID_CLUSTER_NAMESPACE_MESSAGE
+
" & "
InputValidator
.
INVALID_CLUSTER_NAMESPACE_MESSAGE
+
" & "
+
InputValidator
.
INVALID_NAMESPACE_NAMESPACE_MESSAGE
));
+
InputValidator
.
INVALID_NAMESPACE_NAMESPACE_MESSAGE
));
}
}
AppNamespace
createdAppNamespace
=
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
);
AppNamespace
createdAppNamespace
=
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
,
appendNamespacePrefix
);
if
(
portalConfig
.
canAppAdminCreatePrivateNamespace
()
||
createdAppNamespace
.
isPublic
())
{
if
(
portalConfig
.
canAppAdminCreatePrivateNamespace
()
||
createdAppNamespace
.
isPublic
())
{
assignNamespaceRoleToOperator
(
appId
,
appNamespace
.
getName
());
assignNamespaceRoleToOperator
(
appId
,
appNamespace
.
getName
());
...
...
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/repository/AppNamespaceRepository.java
View file @
b949afac
...
@@ -12,7 +12,7 @@ public interface AppNamespaceRepository extends PagingAndSortingRepository<AppNa
...
@@ -12,7 +12,7 @@ public interface AppNamespaceRepository extends PagingAndSortingRepository<AppNa
AppNamespace
findByName
(
String
namespaceName
);
AppNamespace
findByName
(
String
namespaceName
);
AppNamespace
findByNameAndIsPublic
(
String
namespaceName
,
boolean
isPublic
);
List
<
AppNamespace
>
findByNameAndIsPublic
(
String
namespaceName
,
boolean
isPublic
);
List
<
AppNamespace
>
findByIsPublicTrue
();
List
<
AppNamespace
>
findByIsPublicTrue
();
...
...
apollo-portal/src/main/java/com/ctrip/framework/apollo/portal/service/AppNamespaceService.java
View file @
b949afac
...
@@ -9,16 +9,23 @@ import com.ctrip.framework.apollo.core.utils.StringUtils;
...
@@ -9,16 +9,23 @@ import com.ctrip.framework.apollo.core.utils.StringUtils;
import
com.ctrip.framework.apollo.portal.repository.AppNamespaceRepository
;
import
com.ctrip.framework.apollo.portal.repository.AppNamespaceRepository
;
import
com.ctrip.framework.apollo.portal.spi.UserInfoHolder
;
import
com.ctrip.framework.apollo.portal.spi.UserInfoHolder
;
import
com.google.common.base.Joiner
;
import
com.google.common.collect.Sets
;
import
java.util.Set
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.stereotype.Service
;
import
org.springframework.stereotype.Service
;
import
org.springframework.transaction.annotation.Transactional
;
import
org.springframework.transaction.annotation.Transactional
;
import
java.util.List
;
import
java.util.List
;
import
java.util.Objects
;
import
java.util.Objects
;
import
org.springframework.util.CollectionUtils
;
@Service
@Service
public
class
AppNamespaceService
{
public
class
AppNamespaceService
{
private
static
final
int
PRIVATE_APP_NAMESPACE_NOTIFICATION_COUNT
=
5
;
private
static
final
Joiner
APP_NAMESPACE_JOINER
=
Joiner
.
on
(
","
).
skipNulls
();
@Autowired
@Autowired
private
UserInfoHolder
userInfoHolder
;
private
UserInfoHolder
userInfoHolder
;
@Autowired
@Autowired
...
@@ -38,7 +45,17 @@ public class AppNamespaceService {
...
@@ -38,7 +45,17 @@ public class AppNamespaceService {
}
}
public
AppNamespace
findPublicAppNamespace
(
String
namespaceName
)
{
public
AppNamespace
findPublicAppNamespace
(
String
namespaceName
)
{
return
appNamespaceRepository
.
findByNameAndIsPublic
(
namespaceName
,
true
);
List
<
AppNamespace
>
appNamespaces
=
appNamespaceRepository
.
findByNameAndIsPublic
(
namespaceName
,
true
);
if
(
CollectionUtils
.
isEmpty
(
appNamespaces
))
{
return
null
;
}
return
appNamespaces
.
get
(
0
);
}
private
List
<
AppNamespace
>
findAllPrivateAppNamespaces
(
String
namespaceName
)
{
return
appNamespaceRepository
.
findByNameAndIsPublic
(
namespaceName
,
false
);
}
}
public
AppNamespace
findByAppIdAndName
(
String
appId
,
String
namespaceName
)
{
public
AppNamespace
findByAppIdAndName
(
String
appId
,
String
namespaceName
)
{
...
@@ -69,8 +86,12 @@ public class AppNamespaceService {
...
@@ -69,8 +86,12 @@ public class AppNamespaceService {
return
Objects
.
isNull
(
appNamespaceRepository
.
findByAppIdAndName
(
appId
,
namespaceName
));
return
Objects
.
isNull
(
appNamespaceRepository
.
findByAppIdAndName
(
appId
,
namespaceName
));
}
}
@Transactional
public
AppNamespace
createAppNamespaceInLocal
(
AppNamespace
appNamespace
)
{
public
AppNamespace
createAppNamespaceInLocal
(
AppNamespace
appNamespace
)
{
return
createAppNamespaceInLocal
(
appNamespace
,
true
);
}
@Transactional
public
AppNamespace
createAppNamespaceInLocal
(
AppNamespace
appNamespace
,
boolean
appendNamespacePrefix
)
{
String
appId
=
appNamespace
.
getAppId
();
String
appId
=
appNamespace
.
getAppId
();
//add app org id as prefix
//add app org id as prefix
...
@@ -82,7 +103,7 @@ public class AppNamespaceService {
...
@@ -82,7 +103,7 @@ public class AppNamespaceService {
StringBuilder
appNamespaceName
=
new
StringBuilder
();
StringBuilder
appNamespaceName
=
new
StringBuilder
();
//add prefix postfix
//add prefix postfix
appNamespaceName
appNamespaceName
.
append
(
appNamespace
.
isPublic
()
?
app
.
getOrgId
()
+
"."
:
""
)
.
append
(
appNamespace
.
isPublic
()
&&
appendNamespacePrefix
?
app
.
getOrgId
()
+
"."
:
""
)
.
append
(
appNamespace
.
getName
())
.
append
(
appNamespace
.
getName
())
.
append
(
appNamespace
.
formatAsEnum
()
==
ConfigFileFormat
.
Properties
?
""
:
"."
+
appNamespace
.
getFormat
());
.
append
(
appNamespace
.
formatAsEnum
()
==
ConfigFileFormat
.
Properties
?
""
:
"."
+
appNamespace
.
getFormat
());
appNamespace
.
setName
(
appNamespaceName
.
toString
());
appNamespace
.
setName
(
appNamespaceName
.
toString
());
...
@@ -103,12 +124,9 @@ public class AppNamespaceService {
...
@@ -103,12 +124,9 @@ public class AppNamespaceService {
appNamespace
.
setDataChangeLastModifiedBy
(
operator
);
appNamespace
.
setDataChangeLastModifiedBy
(
operator
);
//
unique
check
//
globally uniqueness
check
if
(
appNamespace
.
isPublic
())
{
if
(
appNamespace
.
isPublic
())
{
AppNamespace
publicAppNamespace
=
findPublicAppNamespace
(
appNamespace
.
getName
());
checkAppNamespaceGlobalUniqueness
(
appNamespace
);
if
(
publicAppNamespace
!=
null
)
{
throw
new
BadRequestException
(
"Public AppNamespace "
+
appNamespace
.
getName
()
+
" already exists in appId: "
+
publicAppNamespace
.
getAppId
()
+
"!"
);
}
}
}
if
(!
appNamespace
.
isPublic
()
&&
if
(!
appNamespace
.
isPublic
()
&&
...
@@ -124,6 +142,30 @@ public class AppNamespaceService {
...
@@ -124,6 +142,30 @@ public class AppNamespaceService {
return
createdAppNamespace
;
return
createdAppNamespace
;
}
}
private
void
checkAppNamespaceGlobalUniqueness
(
AppNamespace
appNamespace
)
{
AppNamespace
publicAppNamespace
=
findPublicAppNamespace
(
appNamespace
.
getName
());
if
(
publicAppNamespace
!=
null
)
{
throw
new
BadRequestException
(
"Public AppNamespace "
+
appNamespace
.
getName
()
+
" already exists in appId: "
+
publicAppNamespace
.
getAppId
()
+
"!"
);
}
List
<
AppNamespace
>
privateAppNamespaces
=
findAllPrivateAppNamespaces
(
appNamespace
.
getName
());
if
(!
CollectionUtils
.
isEmpty
(
privateAppNamespaces
))
{
Set
<
String
>
appIds
=
Sets
.
newHashSet
();
for
(
AppNamespace
ans
:
privateAppNamespaces
)
{
appIds
.
add
(
ans
.
getAppId
());
if
(
appIds
.
size
()
==
PRIVATE_APP_NAMESPACE_NOTIFICATION_COUNT
)
{
break
;
}
}
throw
new
BadRequestException
(
"Public AppNamespace "
+
appNamespace
.
getName
()
+
" already exists as private AppNamespace in appId: "
+
APP_NAMESPACE_JOINER
.
join
(
appIds
)
+
", etc. Please select another name!"
);
}
}
@Transactional
@Transactional
public
AppNamespace
deleteAppNamespace
(
String
appId
,
String
namespaceName
)
{
public
AppNamespace
deleteAppNamespace
(
String
appId
,
String
namespaceName
)
{
AppNamespace
appNamespace
=
appNamespaceRepository
.
findByAppIdAndName
(
appId
,
namespaceName
);
AppNamespace
appNamespace
=
appNamespaceRepository
.
findByAppIdAndName
(
appId
,
namespaceName
);
...
...
apollo-portal/src/main/resources/static/namespace.html
View file @
b949afac
...
@@ -95,9 +95,9 @@
...
@@ -95,9 +95,9 @@
<label
class=
"col-sm-3 control-label"
>
<label
class=
"col-sm-3 control-label"
>
<apollorequiredfield></apollorequiredfield>
<apollorequiredfield></apollorequiredfield>
名称
</label>
名称
</label>
<div
class=
"col-sm-
4
"
valdr-form-group
>
<div
class=
"col-sm-
5
"
valdr-form-group
>
<div
ng-class=
"{'input-group':appNamespace.isPublic}"
>
<div
ng-class=
"{'input-group':appNamespace.isPublic
&& appendNamespacePrefix
}"
>
<span
class=
"input-group-addon"
ng-show=
"appNamespace.isPublic"
<span
class=
"input-group-addon"
ng-show=
"appNamespace.isPublic
&& appendNamespacePrefix
"
ng-bind=
"appBaseInfo.namespacePrefix"
></span>
ng-bind=
"appBaseInfo.namespacePrefix"
></span>
<input
type=
"text"
name=
"namespaceName"
class=
"form-control"
<input
type=
"text"
name=
"namespaceName"
class=
"form-control"
ng-model=
"appNamespace.name"
>
ng-model=
"appNamespace.name"
>
...
@@ -116,9 +116,25 @@
...
@@ -116,9 +116,25 @@
</div>
</div>
<span
ng-show=
"appNamespace.isPublic"
ng-bind=
"concatNamespace()"
<span
ng-show=
"appNamespace.isPublic
&& appendNamespacePrefix
"
ng-bind=
"concatNamespace()"
style=
"line-height: 34px;"
></span>
style=
"line-height: 34px;"
></span>
</div>
</div>
<div
class=
"form-group"
ng-show=
"type == 'create' && appNamespace.isPublic"
>
<label
class=
"col-sm-3 control-label"
>
自动添加部门前缀
</label>
<div
class=
"col-sm-6"
valdr-form-group
>
<div>
<label
class=
"checkbox-inline"
>
<input
type=
"checkbox"
ng-model=
"appendNamespacePrefix"
/>
{{appBaseInfo.namespacePrefix}}
</label>
</div>
<small>
(公共Namespace的名称需要全局唯一,添加部门前缀有助于保证全局唯一性)
</small>
</div>
</div>
<div
class=
"form-group"
ng-show=
"type == 'create' && (pageSetting.canAppAdminCreatePrivateNamespace || hasRootPermission)"
>
<div
class=
"form-group"
ng-show=
"type == 'create' && (pageSetting.canAppAdminCreatePrivateNamespace || hasRootPermission)"
>
<label
class=
"col-sm-3 control-label"
>
<label
class=
"col-sm-3 control-label"
>
<apollorequiredfield></apollorequiredfield>
<apollorequiredfield></apollorequiredfield>
...
...
apollo-portal/src/main/resources/static/scripts/controller/NamespaceController.js
View file @
b949afac
...
@@ -11,6 +11,7 @@ namespace_module.controller("LinkNamespaceController",
...
@@ -11,6 +11,7 @@ namespace_module.controller("LinkNamespaceController",
$scope
.
step
=
1
;
$scope
.
step
=
1
;
$scope
.
submitBtnDisabled
=
false
;
$scope
.
submitBtnDisabled
=
false
;
$scope
.
appendNamespacePrefix
=
true
;
PermissionService
.
has_root_permission
().
then
(
function
(
result
)
{
PermissionService
.
has_root_permission
().
then
(
function
(
result
)
{
$scope
.
hasRootPermission
=
result
.
hasPermission
;
$scope
.
hasRootPermission
=
result
.
hasPermission
;
...
@@ -125,7 +126,9 @@ namespace_module.controller("LinkNamespaceController",
...
@@ -125,7 +126,9 @@ namespace_module.controller("LinkNamespaceController",
}
}
$scope
.
submitBtnDisabled
=
true
;
$scope
.
submitBtnDisabled
=
true
;
NamespaceService
.
createAppNamespace
(
$scope
.
appId
,
$scope
.
appNamespace
).
then
(
//only append namespace prefix for public app namespace
var
appendNamespacePrefix
=
$scope
.
appNamespace
.
isPublic
?
$scope
.
appendNamespacePrefix
:
false
;
NamespaceService
.
createAppNamespace
(
$scope
.
appId
,
$scope
.
appNamespace
,
appendNamespacePrefix
).
then
(
function
(
result
)
{
function
(
result
)
{
$scope
.
step
=
2
;
$scope
.
step
=
2
;
setTimeout
(
function
()
{
setTimeout
(
function
()
{
...
...
apollo-portal/src/main/resources/static/scripts/services/NamespaceService.js
View file @
b949afac
...
@@ -12,7 +12,7 @@ appService.service("NamespaceService", ['$resource', '$q', function ($resource,
...
@@ -12,7 +12,7 @@ appService.service("NamespaceService", ['$resource', '$q', function ($resource,
},
},
createAppNamespace
:
{
createAppNamespace
:
{
method
:
'
POST
'
,
method
:
'
POST
'
,
url
:
'
/apps/:appId/appnamespaces
'
,
url
:
'
/apps/:appId/appnamespaces
?appendNamespacePrefix=:appendNamespacePrefix
'
,
isArray
:
false
isArray
:
false
},
},
getNamespacePublishInfo
:
{
getNamespacePublishInfo
:
{
...
@@ -60,11 +60,12 @@ appService.service("NamespaceService", ['$resource', '$q', function ($resource,
...
@@ -60,11 +60,12 @@ appService.service("NamespaceService", ['$resource', '$q', function ($resource,
return
d
.
promise
;
return
d
.
promise
;
}
}
function
createAppNamespace
(
appId
,
appnamespace
)
{
function
createAppNamespace
(
appId
,
appnamespace
,
appendNamespacePrefix
)
{
var
d
=
$q
.
defer
();
var
d
=
$q
.
defer
();
namespace_source
.
createAppNamespace
({
namespace_source
.
createAppNamespace
({
appId
:
appId
appId
:
appId
,
},
appnamespace
,
function
(
result
)
{
appendNamespacePrefix
:
appendNamespacePrefix
},
appnamespace
,
function
(
result
)
{
d
.
resolve
(
result
);
d
.
resolve
(
result
);
},
function
(
result
)
{
},
function
(
result
)
{
d
.
reject
(
result
);
d
.
reject
(
result
);
...
...
apollo-portal/src/test/java/com/ctrip/framework/apollo/portal/service/AppNamespaceServiceTest.java
View file @
b949afac
...
@@ -76,6 +76,31 @@ public class AppNamespaceServiceTest extends AbstractIntegrationTest {
...
@@ -76,6 +76,31 @@ public class AppNamespaceServiceTest extends AbstractIntegrationTest {
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
);
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
);
}
}
@Test
@Sql
(
scripts
=
"/sql/appnamespaceservice/init-appnamespace.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
BEFORE_TEST_METHOD
)
@Sql
(
scripts
=
"/sql/cleanup.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
AFTER_TEST_METHOD
)
public
void
testCreatePublicAppNamespaceNotExistedWithNoAppendnamespacePrefix
()
{
AppNamespace
appNamespace
=
assmbleBaseAppNamespace
();
appNamespace
.
setPublic
(
true
);
appNamespace
.
setName
(
"old"
);
AppNamespace
createdAppNamespace
=
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
,
false
);
Assert
.
assertNotNull
(
createdAppNamespace
);
Assert
.
assertEquals
(
appNamespace
.
getName
(),
createdAppNamespace
.
getName
());
}
@Test
(
expected
=
BadRequestException
.
class
)
@Sql
(
scripts
=
"/sql/appnamespaceservice/init-appnamespace.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
BEFORE_TEST_METHOD
)
@Sql
(
scripts
=
"/sql/cleanup.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
AFTER_TEST_METHOD
)
public
void
testCreatePublicAppNamespaceExistedWithNoAppendnamespacePrefix
()
{
AppNamespace
appNamespace
=
assmbleBaseAppNamespace
();
appNamespace
.
setPublic
(
true
);
appNamespace
.
setName
(
"datasource"
);
appNamespaceService
.
createAppNamespaceInLocal
(
appNamespace
,
false
);
}
@Test
@Test
@Sql
(
scripts
=
"/sql/appnamespaceservice/init-appnamespace.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
BEFORE_TEST_METHOD
)
@Sql
(
scripts
=
"/sql/appnamespaceservice/init-appnamespace.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
BEFORE_TEST_METHOD
)
@Sql
(
scripts
=
"/sql/cleanup.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
AFTER_TEST_METHOD
)
@Sql
(
scripts
=
"/sql/cleanup.sql"
,
executionPhase
=
Sql
.
ExecutionPhase
.
AFTER_TEST_METHOD
)
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment