10 Commits
v1.15 ... v2.03

Author SHA1 Message Date
RobbieHan
ba936d7f9e create cmdb app 2018-12-10 20:32:45 +08:00
RobbieHan
c399b77703 remove .idea 2018-11-27 12:11:16 +08:00
RobbieHan
894fe29e15 change to mysql 2018-11-27 01:05:11 +08:00
RobbieHan
602edea8f8 deployment setting 2018-11-26 21:10:43 +08:00
RobbieHan
9d149a6882 system config 2018-11-17 12:12:05 +08:00
RobbieHan
0b47673759 system config 2018-11-16 23:03:09 +08:00
RobbieHan
e2edef0af2 rbac config 2018-11-16 20:15:05 +08:00
RobbieHan
1f94ffa857 role2menu 2018-11-14 23:40:06 +08:00
RobbieHan
134ea4426f role2user 2018-11-14 19:56:01 +08:00
RobbieHan
04d01aa273 role2uesr 2018-11-14 18:49:00 +08:00
53 changed files with 908 additions and 838 deletions

3
.gitattributes vendored Normal file
View File

@@ -0,0 +1,3 @@
*.js linguist-language=python
*.css linguist-language=python
*.html linguist-language=python

1
.gitignore vendored Normal file
View File

@@ -0,0 +1 @@
.idea

View File

@@ -1,3 +0,0 @@
<component name="ProjectDictionaryState">
<dictionary name="RobbieHan" />
</component>

4
.idea/misc.xml generated
View File

@@ -1,4 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectRootManager" version="2" project-jdk-name="Python 3.6 (sandboxMP)" project-jdk-type="Python SDK" />
</project>

8
.idea/modules.xml generated
View File

@@ -1,8 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ProjectModuleManager">
<modules>
<module fileurl="file://$PROJECT_DIR$/.idea/sandboxMP.iml" filepath="$PROJECT_DIR$/.idea/sandboxMP.iml" />
</modules>
</component>
</project>

32
.idea/sandboxMP.iml generated
View File

@@ -1,32 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<module type="PYTHON_MODULE" version="4">
<component name="FacetManager">
<facet type="django" name="Django">
<configuration>
<option name="rootFolder" value="$MODULE_DIR$" />
<option name="settingsModule" value="sandboxMP/settings.py" />
<option name="manageScript" value="$MODULE_DIR$/manage.py" />
<option name="environment" value="&lt;map/&gt;" />
<option name="doNotUseTestRunner" value="false" />
</configuration>
</facet>
</component>
<component name="NewModuleRootManager">
<content url="file://$MODULE_DIR$">
<sourceFolder url="file://$MODULE_DIR$/apps" isTestSource="false" />
</content>
<orderEntry type="inheritedJdk" />
<orderEntry type="sourceFolder" forTests="false" />
</component>
<component name="TemplatesService">
<option name="TEMPLATE_CONFIGURATION" value="Django" />
<option name="TEMPLATE_FOLDERS">
<list>
<option value="$MODULE_DIR$/../sandboxMP\templates" />
</list>
</option>
</component>
<component name="TestRunnerService">
<option name="PROJECT_TEST_RUNNER" value="Unittests" />
</component>
</module>

6
.idea/vcs.xml generated
View File

@@ -1,6 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="VcsDirectoryMappings">
<mapping directory="$PROJECT_DIR$" vcs="Git" />
</component>
</project>

736
.idea/workspace.xml generated
View File

@@ -1,736 +0,0 @@
<?xml version="1.0" encoding="UTF-8"?>
<project version="4">
<component name="ChangeListManager">
<list default="true" id="80da5b45-7eca-459a-bbe3-5443bc141768" name="Default" comment="">
<change beforePath="$PROJECT_DIR$/apps/system/urls.py" afterPath="$PROJECT_DIR$/apps/system/urls.py" />
<change beforePath="$PROJECT_DIR$/db.sqlite3" afterPath="$PROJECT_DIR$/db.sqlite3" />
</list>
<option name="EXCLUDED_CONVERTED_TO_IGNORED" value="true" />
<option name="TRACKING_ENABLED" value="true" />
<option name="SHOW_DIALOG" value="false" />
<option name="HIGHLIGHT_CONFLICTS" value="true" />
<option name="HIGHLIGHT_NON_ACTIVE_CHANGELIST" value="false" />
<option name="LAST_RESOLUTION" value="IGNORE" />
</component>
<component name="DjangoConsoleOptions" custom-start-script="import sys; print('Python %s on %s' % (sys.version, sys.platform))&#10;import django; print('Django %s' % django.get_version())&#10;sys.path.extend([WORKING_DIR_AND_PYTHON_PATHS])&#10;if 'setup' in dir(django): django.setup()&#10;import django_manage_shell; django_manage_shell.run(PROJECT_ROOT)">
<option name="myCustomStartScript" value="import sys; print('Python %s on %s' % (sys.version, sys.platform))&#10;import django; print('Django %s' % django.get_version())&#10;sys.path.extend([WORKING_DIR_AND_PYTHON_PATHS])&#10;if 'setup' in dir(django): django.setup()&#10;import django_manage_shell; django_manage_shell.run(PROJECT_ROOT)" />
</component>
<component name="FileEditorManager">
<leaf SIDE_TABS_SIZE_LIMIT_KEY="300" />
</component>
<component name="FileTemplateManagerImpl">
<option name="RECENT_TEMPLATES">
<list>
<option value="Python Script" />
<option value="HTML File" />
</list>
</option>
</component>
<component name="FindInProjectRecents">
<findStrings>
<find>reverse</find>
<find>OA</find>
</findStrings>
</component>
<component name="Git.Settings">
<option name="RECENT_GIT_ROOT_PATH" value="$PROJECT_DIR$" />
</component>
<component name="IdeDocumentHistory">
<option name="CHANGED_PATHS">
<list>
<option value="$PROJECT_DIR$/templates/base-left.html" />
<option value="$PROJECT_DIR$/templates/head-footer.html" />
<option value="$PROJECT_DIR$/apps/system/models.py" />
<option value="$PROJECT_DIR$/apps/system/mixin.py" />
<option value="$PROJECT_DIR$/templates/system/system.html" />
<option value="$PROJECT_DIR$/sandboxMP/urls.py" />
<option value="$PROJECT_DIR$/templates/system/system_index.html" />
<option value="$PROJECT_DIR$/apps/system/views.py" />
<option value="$PROJECT_DIR$/apps/system/tests.py" />
<option value="$PROJECT_DIR$/templates/system/structure/structure_create.html" />
<option value="$PROJECT_DIR$/templates/system/structure/strueture_users.html" />
<option value="$PROJECT_DIR$/templates/system/structure/strueture_user.html" />
<option value="$PROJECT_DIR$/templates/system/structure/structure.html" />
<option value="$PROJECT_DIR$/templates/system/structure/structure_user.html" />
<option value="$PROJECT_DIR$/templates/system/users/user_create.html" />
<option value="$PROJECT_DIR$/templates/system/users/user_detail.html" />
<option value="$PROJECT_DIR$/templates/base-static.html" />
<option value="$PROJECT_DIR$/templates/system/users/passwd_change.html" />
<option value="$PROJECT_DIR$/templates/system/users/user.html" />
<option value="$PROJECT_DIR$/apps/system/views_user.py" />
<option value="$PROJECT_DIR$/apps/system/forms.py" />
<option value="$PROJECT_DIR$/apps/system/views.menu.py" />
<option value="$PROJECT_DIR$/templates/system/menu_form.html" />
<option value="$PROJECT_DIR$/apps/system/apps.py" />
<option value="$PROJECT_DIR$/sandboxMP/settings.py" />
<option value="$PROJECT_DIR$/apps/system/views_structure.py" />
<option value="$PROJECT_DIR$/templates/system/menu_update.html" />
<option value="$PROJECT_DIR$/templates/system/menu_list.html" />
<option value="$PROJECT_DIR$/apps/custom.py" />
<option value="$PROJECT_DIR$/templates/system/role_create.html" />
<option value="$PROJECT_DIR$/apps/system/views_menu.py" />
<option value="$PROJECT_DIR$/templates/system/role_update.html" />
<option value="$PROJECT_DIR$/apps/system/urls.py" />
<option value="$PROJECT_DIR$/apps/system/views_role.py" />
<option value="$PROJECT_DIR$/templates/system/role.html" />
</list>
</option>
</component>
<component name="JsBuildToolGruntFileManager" detection-done="true" sorting="DEFINITION_ORDER" />
<component name="JsBuildToolPackageJson" detection-done="true" sorting="DEFINITION_ORDER" />
<component name="JsGulpfileManager">
<detection-done>true</detection-done>
<sorting>DEFINITION_ORDER</sorting>
</component>
<component name="ProjectFrameBounds" extendedState="6">
<option name="x" value="-8" />
<option name="y" value="-8" />
<option name="width" value="1936" />
<option name="height" value="1056" />
</component>
<component name="ProjectInspectionProfilesVisibleTreeState">
<entry key="Project Default">
<profile-state>
<expanded-state>
<State>
<id />
</State>
</expanded-state>
<selected-state>
<State>
<id>AngularJS</id>
</State>
</selected-state>
</profile-state>
</entry>
</component>
<component name="ProjectLevelVcsManager" settingsEditedManually="true" />
<component name="ProjectView">
<navigator currentView="ProjectPane" proportions="" version="1">
<flattenPackages />
<showMembers />
<showModules />
<showLibraryContents />
<hideEmptyPackages />
<abbreviatePackageNames />
<autoscrollToSource />
<autoscrollFromSource />
<sortByType />
<manualOrder />
<foldersAlwaysOnTop value="true" />
</navigator>
<panes>
<pane id="Scratches" />
<pane id="ProjectPane">
<subPane>
<expand>
<path>
<item name="sandboxMP" type="b2602c69:ProjectViewProjectNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
</path>
<path>
<item name="sandboxMP" type="b2602c69:ProjectViewProjectNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
<item name="apps" type="462c0819:PsiDirectoryNode" />
</path>
<path>
<item name="sandboxMP" type="b2602c69:ProjectViewProjectNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
</path>
<path>
<item name="sandboxMP" type="b2602c69:ProjectViewProjectNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
<item name="templates" type="462c0819:PsiDirectoryNode" />
</path>
<path>
<item name="sandboxMP" type="b2602c69:ProjectViewProjectNode" />
<item name="sandboxMP" type="462c0819:PsiDirectoryNode" />
<item name="templates" type="462c0819:PsiDirectoryNode" />
<item name="system" type="462c0819:PsiDirectoryNode" />
</path>
</expand>
<select />
</subPane>
</pane>
<pane id="Scope" />
</panes>
</component>
<component name="PropertiesComponent">
<property name="nodejs_interpreter_path.stuck_in_default_project" value="undefined stuck path" />
<property name="settings.editor.selected.configurable" value="com.jetbrains.python.configuration.PyActiveSdkModuleConfigurable" />
<property name="last_opened_file_path" value="D:/PycharmProject/sandboxOA" />
<property name="WebServerToolWindowFactoryState" value="false" />
<property name="DefaultHtmlFileTemplate" value="HTML File" />
</component>
<component name="PyConsoleOptionsProvider">
<option name="myPythonConsoleState">
<console-settings is-module-sdk="true">
<option name="myUseModuleSdk" value="true" />
</console-settings>
</option>
</component>
<component name="RecentsManager">
<key name="MoveFile.RECENT_KEYS">
<recent name="D:\ProjectFile\sandboxMP\templates\system" />
<recent name="D:\ProjectFile\sandboxMP\apps" />
</key>
<key name="CopyFile.RECENT_KEYS">
<recent name="D:\ProjectFile\sandboxMP\templates\system" />
<recent name="D:\ProjectFile\sandboxMP\templates" />
<recent name="D:\ProjectFile\sandboxMP\templates\system\users" />
<recent name="D:\ProjectFile\sandboxMP\templates\system\structure" />
<recent name="D:\ProjectFile\sandboxMP\apps\system" />
</key>
</component>
<component name="RunDashboard">
<option name="ruleStates">
<list>
<RuleState>
<option name="name" value="ConfigurationTypeDashboardGroupingRule" />
</RuleState>
<RuleState>
<option name="name" value="StatusDashboardGroupingRule" />
</RuleState>
</list>
</option>
</component>
<component name="RunManager">
<configuration name="sandboxMP" type="Python.DjangoServer" factoryName="Django server">
<option name="INTERPRETER_OPTIONS" value="" />
<option name="PARENT_ENVS" value="true" />
<envs>
<env name="PYTHONUNBUFFERED" value="1" />
<env name="DJANGO_SETTINGS_MODULE" value="sandboxMP.settings" />
</envs>
<option name="SDK_HOME" value="" />
<option name="WORKING_DIRECTORY" value="" />
<option name="IS_MODULE_SDK" value="false" />
<option name="ADD_CONTENT_ROOTS" value="true" />
<option name="ADD_SOURCE_ROOTS" value="true" />
<module name="sandboxMP" />
<option name="launchJavascriptDebuger" value="false" />
<option name="port" value="8000" />
<option name="host" value="" />
<option name="additionalOptions" value="" />
<option name="browserUrl" value="" />
<option name="runTestServer" value="false" />
<option name="runNoReload" value="false" />
<option name="useCustomRunCommand" value="false" />
<option name="customRunCommand" value="" />
</configuration>
</component>
<component name="ShelveChangesManager" show_recycled="false">
<option name="remove_strategy" value="false" />
</component>
<component name="SvnConfiguration">
<configuration />
</component>
<component name="TaskManager">
<task active="true" id="Default" summary="Default task">
<changelist id="80da5b45-7eca-459a-bbe3-5443bc141768" name="Default" comment="" />
<created>1539589405377</created>
<option name="number" value="Default" />
<option name="presentableId" value="Default" />
<updated>1539589405377</updated>
</task>
<servers />
</component>
<component name="TodoView">
<todo-panel id="selected-file">
<is-autoscroll-to-source value="true" />
</todo-panel>
<todo-panel id="all">
<are-packages-shown value="true" />
<is-autoscroll-to-source value="true" />
</todo-panel>
</component>
<component name="ToolWindowManager">
<frame x="-8" y="-8" width="1936" height="1056" extended-state="6" />
<layout>
<window_info id="TODO" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="6" side_tool="false" content_ui="tabs" />
<window_info id="Event Log" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.24156693" sideWeight="0.5042644" order="7" side_tool="true" content_ui="tabs" />
<window_info id="Version Control" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Python Console" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Run" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.1936888" sideWeight="0.49573562" order="2" side_tool="false" content_ui="tabs" />
<window_info id="Mongo Explorer" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Terminal" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Project" active="true" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.14978679" sideWeight="0.5" order="0" side_tool="false" content_ui="combo" />
<window_info id="Docker" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="false" weight="0.33" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Database" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="SciView" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Structure" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.18656716" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
<window_info id="Favorites" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="2" side_tool="true" content_ui="tabs" />
<window_info id="Debug" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.21650879" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Cvs" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="4" side_tool="false" content_ui="tabs" />
<window_info id="TODO" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="6" side_tool="false" content_ui="tabs" />
<window_info id="Message" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="0" side_tool="false" content_ui="tabs" />
<window_info id="Commander" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="0" side_tool="false" content_ui="tabs" />
<window_info id="Event Log" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.24156693" sideWeight="0.5042644" order="7" side_tool="true" content_ui="tabs" />
<window_info id="Inspection" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.4" sideWeight="0.5" order="5" side_tool="false" content_ui="tabs" />
<window_info id="Version Control" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Python Console" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Run" active="true" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.23274696" sideWeight="0.49573562" order="2" side_tool="false" content_ui="tabs" />
<window_info id="manage.py@sandboxMP" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.28073993" sideWeight="0.5" order="8" side_tool="false" content_ui="tabs" />
<window_info id="Mongo Explorer" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Terminal" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.3297062" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Hierarchy" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="2" side_tool="false" content_ui="combo" />
<window_info id="Project" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="true" show_stripe_button="true" weight="0.2012894" sideWeight="0.5" order="0" side_tool="false" content_ui="combo" />
<window_info id="Docker" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="false" weight="0.33" sideWeight="0.5" order="7" side_tool="false" content_ui="tabs" />
<window_info id="Find" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
<window_info id="Database" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="SciView" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
<window_info id="Structure" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.18656716" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
<window_info id="Ant Build" active="false" anchor="right" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.25" sideWeight="0.5" order="1" side_tool="false" content_ui="tabs" />
<window_info id="Favorites" active="false" anchor="left" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.33" sideWeight="0.5" order="2" side_tool="true" content_ui="tabs" />
<window_info id="Debug" active="false" anchor="bottom" auto_hide="false" internal_type="DOCKED" type="DOCKED" visible="false" show_stripe_button="true" weight="0.21650879" sideWeight="0.5" order="3" side_tool="false" content_ui="tabs" />
</layout>
</component>
<component name="TypeScriptGeneratedFilesManager">
<option name="version" value="1" />
</component>
<component name="VcsContentAnnotationSettings">
<option name="myLimit" value="2678400000" />
</component>
<component name="XDebuggerManager">
<breakpoint-manager>
<option name="time" value="24" />
</breakpoint-manager>
<watches-manager />
</component>
<component name="editorHistoryManager">
<entry file="file://$PROJECT_DIR$/templates/index.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="238">
<caret line="14" column="14" lean-forward="true" selection-start-line="14" selection-start-column="14" selection-end-line="14" selection-end-column="14" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/base-layer.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="476">
<caret line="28" column="22" lean-forward="true" selection-start-line="28" selection-start-column="22" selection-end-line="28" selection-end-column="22" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/base-left.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="483">
<caret line="36" column="13" lean-forward="true" selection-start-line="36" selection-start-column="13" selection-end-line="36" selection-end-column="13" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/views.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="153">
<caret line="9" column="58" lean-forward="true" selection-start-line="9" selection-start-column="58" selection-end-line="9" selection-end-column="58" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/system_index.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="204">
<caret line="12" column="0" lean-forward="true" selection-start-line="12" selection-start-column="0" selection-end-line="12" selection-end-column="0" />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/urls/conf.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="68">
<caret line="11" column="15" lean-forward="true" selection-start-line="11" selection-start-column="15" selection-end-line="11" selection-end-column="15" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/tests.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="51">
<caret line="3" column="0" lean-forward="false" selection-start-line="3" selection-start-column="0" selection-end-line="3" selection-end-column="0" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/__init__.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="0">
<caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/braces/views/_ajax.py" />
<entry file="file://$PROJECT_DIR$/templates/system/structure/structure_create.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="524">
<caret line="89" column="11" lean-forward="true" selection-start-line="89" selection-start-column="11" selection-end-line="89" selection-end-column="11" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/structure/structure_user.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-15">
<caret line="29" column="95" lean-forward="true" selection-start-line="29" selection-start-column="95" selection-end-line="29" selection-end-column="95" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/structure/structure.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="836">
<caret line="238" column="22" lean-forward="false" selection-start-line="238" selection-start-column="22" selection-end-line="238" selection-end-column="22" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/static/plugins/datatables/dataTables.const-1.js">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="68">
<caret line="4" column="8" lean-forward="false" selection-start-line="4" selection-start-column="8" selection-end-line="4" selection-end-column="8" />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/urls/resolvers.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="260">
<caret line="220" column="33" lean-forward="true" selection-start-line="220" selection-start-column="33" selection-end-line="220" selection-end-column="33" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/users/user_create.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="1396">
<caret line="129" column="26" lean-forward="false" selection-start-line="129" selection-start-column="26" selection-end-line="129" selection-end-column="26" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/head-footer.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="1598">
<caret line="94" column="22" lean-forward="true" selection-start-line="94" selection-start-column="22" selection-end-line="94" selection-end-column="22" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/base-static.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="238">
<caret line="14" column="73" lean-forward="true" selection-start-line="14" selection-start-column="73" selection-end-line="14" selection-end-column="73" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/users/user_detail.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="967">
<caret line="191" column="14" lean-forward="false" selection-start-line="191" selection-start-column="14" selection-end-line="191" selection-end-column="14" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/users/passwd_change.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="459">
<caret line="90" column="0" lean-forward="true" selection-start-line="90" selection-start-column="0" selection-end-line="90" selection-end-column="0" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/contrib/auth/decorators.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-459">
<caret line="9" column="57" lean-forward="false" selection-start-line="9" selection-start-column="57" selection-end-line="9" selection-end-column="57" />
<folding>
<element signature="e#0#27#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/sandboxMP/urls.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="493">
<caret line="29" column="63" lean-forward="true" selection-start-line="29" selection-start-column="63" selection-end-line="30" selection-end-column="0" />
<folding>
<element signature="e#633#665#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/db/models/base.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="238">
<caret line="100" column="8" lean-forward="false" selection-start-line="100" selection-start-column="8" selection-end-line="100" selection-end-column="8" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/utils/encoding.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-1649">
<caret line="121" column="4" lean-forward="false" selection-start-line="121" selection-start-column="4" selection-end-line="121" selection-end-column="4" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/contrib/flatpages/models.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="595">
<caret line="39" column="22" lean-forward="false" selection-start-line="39" selection-start-column="22" selection-end-line="39" selection-end-column="22" />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/db/models/__init__.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-204">
<caret line="0" column="0" lean-forward="false" selection-start-line="0" selection-start-column="0" selection-end-line="0" selection-end-column="0" />
<folding>
<element signature="e#0#53#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/forms/models.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="230">
<caret line="472" column="4" lean-forward="false" selection-start-line="472" selection-start-column="4" selection-end-line="472" selection-end-column="4" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/users/user.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="500">
<caret line="67" column="35" lean-forward="true" selection-start-line="67" selection-start-column="35" selection-end-line="67" selection-end-column="35" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/users/login.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="170">
<caret line="10" column="57" lean-forward="true" selection-start-line="10" selection-start-column="57" selection-end-line="10" selection-end-column="57" />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/views/generic/__init__.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="187">
<caret line="11" column="11" lean-forward="false" selection-start-line="11" selection-start-column="11" selection-end-line="11" selection-end-column="11" />
<folding>
<element signature="e#0#70#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/forms.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="432">
<caret line="127" column="0" lean-forward="false" selection-start-line="127" selection-start-column="0" selection-end-line="127" selection-end-column="0" />
<folding>
<element signature="e#73#82#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/mixin.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="119">
<caret line="7" column="6" lean-forward="false" selection-start-line="7" selection-start-column="6" selection-end-line="7" selection-end-column="6" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/views_user.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-815">
<caret line="62" column="53" lean-forward="false" selection-start-line="62" selection-start-column="53" selection-end-line="62" selection-end-column="53" />
<folding>
<element signature="e#78#87#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/apps.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="85">
<caret line="5" column="0" lean-forward="true" selection-start-line="5" selection-start-column="0" selection-end-line="5" selection-end-column="0" />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/sandboxMP/settings.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="221">
<caret line="56" column="38" lean-forward="true" selection-start-line="56" selection-start-column="38" selection-end-line="56" selection-end-column="38" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/menu_form.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="1122">
<caret line="66" column="49" lean-forward="false" selection-start-line="66" selection-start-column="49" selection-end-line="66" selection-end-column="49" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/models.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="528">
<caret line="72" column="24" lean-forward="true" selection-start-line="72" selection-start-column="24" selection-end-line="72" selection-end-column="24" />
<folding>
<element signature="e#0#28#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/views/generic/base.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="197">
<caret line="130" column="33" lean-forward="true" selection-start-line="130" selection-start-column="4" selection-end-line="130" selection-end-column="33" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/views/generic/detail.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="78">
<caret line="114" column="33" lean-forward="true" selection-start-line="114" selection-start-column="4" selection-end-line="114" selection-end-column="33" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/shortcuts.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="342">
<caret line="56" column="50" lean-forward="true" selection-start-line="56" selection-start-column="21" selection-end-line="56" selection-end-column="50" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/http/response.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="-1063">
<caret line="475" column="6" lean-forward="false" selection-start-line="475" selection-start-column="6" selection-end-line="475" selection-end-column="6" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$USER_HOME$/Envs/sandboxMP/Lib/site-packages/django/views/generic/edit.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="971">
<caret line="181" column="6" lean-forward="false" selection-start-line="181" selection-start-column="6" selection-end-line="181" selection-end-column="6" />
<folding>
<element signature="e#559#654#0" expanded="false" />
<element signature="e#690#758#0" expanded="false" />
<element signature="e#798#864#0" expanded="false" />
<element signature="e#915#1106#0" expanded="false" />
<element signature="e#1147#1527#0" expanded="false" />
<element signature="e#1568#1819#0" expanded="false" />
<element signature="e#1861#1978#0" expanded="false" />
<element signature="e#2022#2149#0" expanded="false" />
<element signature="e#2201#2373#0" expanded="false" />
<element signature="e#2554#3721#0" expanded="false" />
<element signature="e#3762#3978#0" expanded="false" />
<element signature="e#4019#4503#0" expanded="false" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/views_structure.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="238">
<caret line="14" column="5" lean-forward="false" selection-start-line="14" selection-start-column="5" selection-end-line="14" selection-end-column="5" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/menu_update.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="623">
<caret line="100" column="0" lean-forward="true" selection-start-line="100" selection-start-column="0" selection-end-line="100" selection-end-column="0" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/menu_list.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="606">
<caret line="160" column="11" lean-forward="true" selection-start-line="160" selection-start-column="11" selection-end-line="160" selection-end-column="11" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/custom.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="691">
<caret line="55" column="53" lean-forward="true" selection-start-line="55" selection-start-column="53" selection-end-line="55" selection-end-column="53" />
<folding>
<element signature="e#73#84#0" expanded="true" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/role_update.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="657">
<caret line="80" column="14" lean-forward="false" selection-start-line="80" selection-start-column="14" selection-end-line="80" selection-end-column="14" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/views_role.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="595">
<caret line="35" column="28" lean-forward="false" selection-start-line="35" selection-start-column="28" selection-end-line="35" selection-end-column="28" />
<folding>
<element signature="e#78#89#0" expanded="true" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/views_menu.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="136">
<caret line="8" column="16" lean-forward="true" selection-start-line="8" selection-start-column="16" selection-end-line="9" selection-end-column="22" />
<folding>
<element signature="e#0#41#0" expanded="true" />
</folding>
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/role.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="657">
<caret line="145" column="1" lean-forward="true" selection-start-line="145" selection-start-column="1" selection-end-line="145" selection-end-column="1" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/templates/system/role_form.html">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="504">
<caret line="70" column="11" lean-forward="true" selection-start-line="70" selection-start-column="11" selection-end-line="70" selection-end-column="11" />
<folding />
</state>
</provider>
</entry>
<entry file="file://$PROJECT_DIR$/apps/system/urls.py">
<provider selected="true" editor-type-id="text-editor">
<state relative-caret-position="578">
<caret line="34" column="0" lean-forward="true" selection-start-line="34" selection-start-column="0" selection-end-line="34" selection-end-column="0" />
<folding>
<element signature="e#0#28#0" expanded="true" />
</folding>
</state>
</provider>
</entry>
</component>
<component name="masterDetails">
<states>
<state key="ScopeChooserConfigurable.UI">
<settings>
<splitter-proportions>
<option name="proportions">
<list>
<option value="0.2" />
</list>
</option>
</splitter-proportions>
</settings>
</state>
</states>
</component>
</project>

0
apps/cmdb/__init__.py Normal file
View File

3
apps/cmdb/admin.py Normal file
View File

@@ -0,0 +1,3 @@
from django.contrib import admin
# Register your models here.

5
apps/cmdb/apps.py Normal file
View File

@@ -0,0 +1,5 @@
from django.apps import AppConfig
class CmdbConfig(AppConfig):
name = 'cmdb'

View File

22
apps/cmdb/models.py Normal file
View File

@@ -0,0 +1,22 @@
from django.db import models
# Create your models here.
class AbstractMode(models.Model):
parent = models.ForeignKey(
'self', blank=True, null=True, on_delete=models.SET_NULL, related_name='child'
)
class Meta:
abstract = True
class Code(AbstractMode):
key = models.CharField(max_length=80, verbose_name='')
value = models.CharField(max_length=80, verbose_name='')
desc = models.BooleanField(default=True, verbose_name='备注')
class Meta:
verbose_name = '字典'
verbose_name_plural = verbose_name

3
apps/cmdb/tests.py Normal file
View File

@@ -0,0 +1,3 @@
from django.test import TestCase
# Create your tests here.

9
apps/cmdb/urls.py Normal file
View File

@@ -0,0 +1,9 @@
from django.urls import path
from .views import CmdbView
app_name = 'cmdb'
urlpatterns = [
path('', CmdbView.as_view(), name='index'),
]

9
apps/cmdb/views.py Normal file
View File

@@ -0,0 +1,9 @@
from django.views.generic import TemplateView
from system.mixin import LoginRequiredMixin
from custom import BreadcrumbMixin
class CmdbView(LoginRequiredMixin, BreadcrumbMixin, TemplateView):
template_name = 'cmdb/cmdb_index.html'

View File

@@ -9,9 +9,20 @@ from django.shortcuts import HttpResponse
from django.http import Http404
from system.mixin import LoginRequiredMixin
from system.models import Menu
class BreadcrumbMixin:
def get_context_data(self, **kwargs):
menu = Menu.get_menu_by_request_url(url=self.request.path_info)
if menu is not None:
kwargs.update(menu)
return super().get_context_data(**kwargs)
class SandboxGetObjectMixin:
def get_object(self, queryset=None):
if queryset is None:
@@ -50,7 +61,7 @@ class SandboxCreateView(LoginRequiredMixin, SandboxEditViewMixin, CreateView):
class SandboxUpdateView(LoginRequiredMixin, SandboxEditViewMixin, SandboxGetObjectMixin, UpdateView):
"""View for updating an object, with a response rendered by a template."""
def post(self, request, *args, **kwargs):
self.object = self.get_object()
return super().post(request, *args, **kwargs)
return super().post(request, *args, **kwargs)

Binary file not shown.

100
apps/system/middleware.py Normal file
View File

@@ -0,0 +1,100 @@
import re
from django.utils.deprecation import MiddlewareMixin
from django.conf import settings
from django.shortcuts import render
class MenuCollection(MiddlewareMixin):
def get_user(self, request):
return request.user
def get_menu_from_role(self, request, user=None):
if user is None:
user = self.get_user(request)
try:
menus = user.roles.values(
'permissions__id',
'permissions__name',
'permissions__url',
'permissions__icon',
'permissions__code',
'permissions__parent'
).distinct()
return [menu for menu in menus if menu['permissions__id'] is not None]
except AttributeError:
return None
def get_permission_url(self, request):
role_menus = self.get_menu_from_role(request)
if role_menus is not None:
permission_url_list = [menu['permissions__url'] for menu in role_menus]
return permission_url_list
def get_permission_menu(self, request):
permission_menu_list = []
role_menus = self.get_menu_from_role(request)
if role_menus is not None:
for item in role_menus:
menu = {
'id': item['permissions__id'],
'name': item['permissions__name'],
'url': item['permissions__url'],
'icon': item['permissions__icon'],
'code': item['permissions__code'],
'parent': item['permissions__parent'],
'status': False,
'sub_menu': [],
}
permission_menu_list.append(menu)
return permission_menu_list
def get_top_reveal_menu(self, request):
top_menu = []
permission_menu_dict = {}
request_url = request.path_info
permission_menu_list = self.get_permission_menu(request)
if permission_menu_list is not None:
for menu in permission_menu_list:
url = menu['url']
if url and re.match(url, request_url):
menu['status'] = True
if menu['parent'] is None:
top_menu.insert(0, menu)
permission_menu_dict[menu['id']] = menu
menu_data = []
for i in permission_menu_dict:
if permission_menu_dict[i]['parent']:
pid = permission_menu_dict[i]['parent']
parent_menu = permission_menu_dict[pid]
parent_menu['sub_menu'].append(permission_menu_dict[i])
else:
menu_data.append(permission_menu_dict[i])
if [menu['sub_menu'] for menu in menu_data if menu['url'] in request_url]:
reveal_menu = [menu['sub_menu'] for menu in menu_data if menu['url'] in request_url][0]
else:
reveal_menu = None
return top_menu, reveal_menu
def process_request(self, request):
if self.get_top_reveal_menu(request):
request.top_menu, request.reveal_menu = self.get_top_reveal_menu(request)
request.permission_url_list = self.get_permission_url(request)
class RbacMiddleware(MiddlewareMixin):
def process_request(self, request):
if hasattr(request, 'permission_url_list'):
request_url = request.path_info
permission_url = request.permission_url_list
for url in settings.SAFE_URL:
if re.match(url, request_url):
return None
if request_url in permission_url:
return None
else:
return render(request, 'page404.html')

View File

@@ -0,0 +1,22 @@
# Generated by Django 2.1.2 on 2018-11-15 21:24
from django.db import migrations, models
class Migration(migrations.Migration):
dependencies = [
('system', '0001_initial'),
]
operations = [
migrations.AlterModelOptions(
name='menu',
options={'ordering': ['number'], 'verbose_name': '菜单', 'verbose_name_plural': '菜单'},
),
migrations.AddField(
model_name='menu',
name='number',
field=models.FloatField(blank=True, null=True, verbose_name='编号'),
),
]

View File

@@ -11,6 +11,7 @@ class Menu(models.Model):
icon = models.CharField(max_length=50, null=True, blank=True, verbose_name="图标")
code = models.CharField(max_length=50, null=True, blank=True, verbose_name="编码")
url = models.CharField(max_length=128, unique=True, null=True, blank=True)
number = models.FloatField(null=True, blank=True, verbose_name="编号")
def __str__(self):
return self.name
@@ -18,10 +19,14 @@ class Menu(models.Model):
class Meta:
verbose_name = '菜单'
verbose_name_plural = verbose_name
ordering = ['number']
@classmethod
def get_menu_by_request_url(cls, url):
return dict(menu=Menu.objects.get(url=url))
try:
return dict(menu=Menu.objects.get(url=url))
except:
None
class Role(models.Model):

View File

@@ -31,4 +31,8 @@ urlpatterns = [
path('rbac/role/create/', views_role.RoleCreateView.as_view(), name='rbac-role-create'),
path('rbac/role/list/', views_role.RoleListView.as_view(), name='rbac-role-list'),
path('rbac/role/update/', views_role.RoleUpdateView.as_view(), name='rbac-role-update'),
path('rbac/role/delete/', views_role.RoleDeleteView.as_view(), name='rbac-role-delete'),
path('rbac/role/role2user/', views_role.Role2UserView.as_view(), name="rbac-role-role2user"),
path('rbac/role/role2menu/', views_role.Role2MenuView.as_view(), name="rbac-role-role2menu"),
path('rbac/role/role2menu_list/', views_role.Role2MenuListView.as_view(), name="rbac-role-role2menu_list"),
]

View File

@@ -1,11 +1,10 @@
from django.shortcuts import render
from django.views.generic.base import View
from django.views.generic import TemplateView
from .mixin import LoginRequiredMixin
from custom import BreadcrumbMixin
class SystemView(LoginRequiredMixin, View):
class SystemView(LoginRequiredMixin, BreadcrumbMixin, TemplateView):
def get(self, request):
return render(request, 'system/system_index.html')
template_name = 'system/system_index.html'

View File

@@ -1,17 +1,20 @@
from django.views.generic import ListView
from .mixin import LoginRequiredMixin
from apps.custom import SandboxCreateView, SandboxUpdateView
from apps.custom import SandboxCreateView, SandboxUpdateView, BreadcrumbMixin
from .models import Menu
class MenuCreateView(SandboxCreateView):
model = Menu
fields = '__all__'
extra_context = dict(menu_all=Menu.objects.all())
def get_context_data(self, **kwargs):
kwargs['menu_all'] = Menu.objects.all()
return super().get_context_data(**kwargs)
class MenuListView(LoginRequiredMixin, ListView):
class MenuListView(LoginRequiredMixin, BreadcrumbMixin, ListView):
model = Menu
context_object_name = 'menu_all'
@@ -20,4 +23,7 @@ class MenuUpdateView(SandboxUpdateView):
model = Menu
fields = '__all__'
template_name_suffix = '_update'
extra_context = dict(menu_all=Menu.objects.all())
def get_context_data(self, **kwargs):
kwargs['menu_all'] = Menu.objects.all()
return super().get_context_data(**kwargs)

View File

@@ -5,15 +5,19 @@
import json
from django.views.generic.base import View
from django.shortcuts import HttpResponse
from django.shortcuts import HttpResponse, get_object_or_404
from django.views.generic import TemplateView
from django.contrib.auth import get_user_model
from django.shortcuts import render
from .mixin import LoginRequiredMixin
from .models import Role
from custom import SandboxCreateView, SandboxUpdateView
from .models import Role, Menu
from custom import SandboxCreateView, SandboxUpdateView, BreadcrumbMixin
User = get_user_model()
class RoleView(LoginRequiredMixin, TemplateView):
class RoleView(LoginRequiredMixin, BreadcrumbMixin, TemplateView):
template_name = 'system/role.html'
@@ -34,3 +38,81 @@ class RoleUpdateView(SandboxUpdateView):
model = Role
fields = '__all__'
template_name_suffix = '_update'
class RoleDeleteView(LoginRequiredMixin, View):
def post(self, request):
ret = dict(result=False)
if 'id' in request.POST and request.POST['id']:
id_list = map(int, request.POST['id'].split(','))
Role.objects.filter(id__in=id_list).delete()
ret['result'] = True
return HttpResponse(json.dumps(ret), content_type='application/json')
class Role2UserView(LoginRequiredMixin, View):
"""
角色关联用户
"""
def get(self, request):
if 'id' in request.GET and request.GET['id']:
role = get_object_or_404(Role, pk=int(request.GET.get('id')))
added_users = role.userprofile_set.all()
all_users = User.objects.all()
un_add_users = set(all_users).difference(added_users)
ret = dict(role=role, added_users=added_users, un_add_users=list(un_add_users))
return render(request, 'system/role_role2user.html', ret)
def post(self, request):
res = dict(result=False)
id_list = None
role = get_object_or_404(Role, pk=int(request.POST.get('id')))
if 'to' in request.POST and request.POST['to']:
id_list = map(int, request.POST.getlist('to', []))
role.userprofile_set.clear()
if id_list:
for user in User.objects.filter(id__in=id_list):
role.userprofile_set.add(user)
res['result'] = True
return HttpResponse(json.dumps(res), content_type='application/json')
class Role2MenuView(LoginRequiredMixin, View):
"""
角色绑定菜单
"""
def get(self, request):
if 'id' in request.GET and request.GET['id']:
role = get_object_or_404(Role, pk=request.GET['id'])
ret = dict(role=role)
return render(request, 'system/role_role2menu.html', ret)
def post(self, request):
res = dict(result=False)
role = get_object_or_404(Role, pk=request.POST['id'])
tree = json.loads(self.request.POST['tree'])
role.permissions.clear()
for menu in tree:
if menu['checked'] is True:
menu_checked = get_object_or_404(Menu, pk=menu['id'])
role.permissions.add(menu_checked)
res['result'] = True
return HttpResponse(json.dumps(res), content_type='application/json')
class Role2MenuListView(LoginRequiredMixin, View):
"""
获取zTree菜单列表
"""
def get(self, request):
fields = ['id', 'name', 'parent']
if 'id' in request.GET and request.GET['id']:
role = Role.objects.get(id=request.GET.get('id'))
role_menus = role.permissions.values(*fields)
ret = dict(data=list(role_menus))
else:
menus = Menu.objects.all()
ret = dict(data=list(menus.values(*fields)))
return HttpResponse(json.dumps(ret), content_type='application/json')

View File

@@ -14,11 +14,12 @@ from django.contrib.auth import get_user_model
from .mixin import LoginRequiredMixin
from .models import Structure
from .forms import StructureForm
from apps.custom import BreadcrumbMixin
User = get_user_model()
class StructureView(LoginRequiredMixin, TemplateView):
class StructureView(LoginRequiredMixin, BreadcrumbMixin, TemplateView):
template_name = 'system/structure/structure.html'

View File

@@ -17,6 +17,7 @@ from django.db.models import Q
from .forms import LoginForm, UserCreateForm, UserUpdateForm, PasswordChangeForm
from .mixin import LoginRequiredMixin
from .models import Structure, Role
from apps.custom import BreadcrumbMixin
User = get_user_model()
@@ -63,7 +64,7 @@ class LogoutView(View):
return HttpResponseRedirect(reverse('login'))
class UserView(LoginRequiredMixin, TemplateView):
class UserView(LoginRequiredMixin, BreadcrumbMixin, TemplateView):
template_name = 'system/users/user.html'

Binary file not shown.

2
requirements/dev.txt Normal file
View File

@@ -0,0 +1,2 @@
django==2.1.2
pillow==5.3.0

2
requirements/pro.txt Normal file
View File

@@ -0,0 +1,2 @@
django==2.1.2
pillow==5.3.0

View File

@@ -27,7 +27,7 @@ SECRET_KEY = 'o6ijylqj@xxpvxzybcv2khtu5zk@y56nt4ptsb4dbgmdz8t%q='
# SECURITY WARNING: don't run with debug turned on in production!
DEBUG = True
ALLOWED_HOSTS = []
ALLOWED_HOSTS = ['*']
# Application definition
@@ -40,6 +40,7 @@ INSTALLED_APPS = [
'django.contrib.messages',
'django.contrib.staticfiles',
'system',
'cmdb',
]
MIDDLEWARE = [
@@ -50,6 +51,8 @@ MIDDLEWARE = [
'django.contrib.auth.middleware.AuthenticationMiddleware',
'django.contrib.messages.middleware.MessageMiddleware',
'django.middleware.clickjacking.XFrameOptionsMiddleware',
'apps.system.middleware.MenuCollection',
'apps.system.middleware.RbacMiddleware',
]
ROOT_URLCONF = 'sandboxMP.urls'
@@ -79,14 +82,24 @@ WSGI_APPLICATION = 'sandboxMP.wsgi.application'
# Database
# https://docs.djangoproject.com/en/2.1/ref/settings/#databases
# DATABASES = {
# 'default': {
# 'ENGINE': 'django.db.backends.sqlite3',
# 'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
# }
# }
DATABASES = {
'default': {
'ENGINE': 'django.db.backends.sqlite3',
'NAME': os.path.join(BASE_DIR, 'db.sqlite3'),
'ENGINE': 'django.db.backends.mysql',
'NAME': 'sandboxMP',
'HOST': '127.0.0.1',
'USER': 'ddadmin',
'PASSWORD': '1234@abcd.com',
'PORT': '3306'
}
}
# Password validation
# https://docs.djangoproject.com/en/2.1/ref/settings/#auth-password-validators
@@ -132,3 +145,19 @@ MEDIA_URL = '/media/'
MEDIA_ROOT = os.path.join(BASE_DIR, 'media')
LOGIN_URL = '/login/'
# safe url
SAFE_URL = [r'^/$',
'/login/',
'/logout',
'/index/',
'/media/',
'/admin/',
'/ckeditor/',
]
# session timeout
SESSION_COOKIE_AGE = 60 * 20
SESSION_EXPIRE_AT_BROWSER_CLOSE = True
SESSION_SAVE_EVERY_REQUEST = True

View File

@@ -28,6 +28,7 @@ urlpatterns = [
path('login/', LoginView.as_view(), name='login'),
path('logout/', LogoutView.as_view(), name='logout'),
path('system/', include('system.urls', namespace='system')),
path('cmdb/', include('cmdb.urls', namespace='cmdb')),
]

View File

@@ -21,20 +21,32 @@
<!-- /.search form -->
<!-- Sidebar Menu -->
<ul class="sidebar-menu">
<ul class="sidebar-menu">
<li class="header"></li>
<!-- Optionally, you can add icons to the links -->
<li class="treeview">
<a href="#"><i class="fa fa-calendar"></i> <span>一级菜单</span>
<span class="pull-right-container">
<i class="fa fa-angle-left pull-right"></i>
</span>
</a>
<ul class="treeview-menu">
<li><a href="#"><i class="fa fa-caret-right"></i>二级菜单</a></li>
<li><a href="#"><i class="fa fa-caret-right"></i>二级菜单</a></li>
</ul>
</li>
{% for menu in request.reveal_menu %}
{% if not menu.url %}
<li class="treeview" id="{{ menu.code }}">
<a href="">
<i class="{{ menu.icon }}"></i><span>{{ menu.name }}</span>
<span class="pull-right-container"><i class="fa fa-angle-left pull-right"></i>
</span>
</a>
<ul class="treeview-menu">
{% for sub in menu.sub_menu %}
<li id="{{ sub.code }}">
<a href="{{ sub.url }}"><i class="fa fa-caret-right"></i>{{ sub.name }}</a>
</li>
{% endfor %}
</ul>
</li>
{% else %}
<li id="{{ menu.code }}">
<a href="{{ menu.url }}"><i class="{{ menu.icon }}"></i><span>{{ menu.name }}</span>
</a>
</li>
{% endif %}
{% endfor %}
</ul>
<!-- /.sidebar-menu -->
</section>
@@ -44,7 +56,14 @@
<!-- Content Wrapper. Contains page content -->
<div class="content-wrapper">
<section class="content-header margin-bottom">
<ol class="breadcrumb">
{% if menu.parent %}
<li class="active"><a href="{{ menu.parent.url | default:'' }}">{{ menu.parent.name }}</a></li>
{% endif %}
<li class="active"><a href="{{ menu.url }}">{{ menu.name }}</a></li>
</ol>
</section>
{% block content %}

View File

@@ -0,0 +1,20 @@
{% extends "base-left.html" %}
{% load staticfiles %}
{% block css %}{% endblock %}
{% block content %}
<!-- Main content -->
<section class="content">
这里是配置管理首页临时内容
</section>
<!-- /.content -->
{% endblock %}
{% block javascripts %}
{% endblock %}

View File

@@ -20,9 +20,13 @@
<span class="sr-only">Toggle navigation</span>
</a>
<div class="collapse navbar-collapse pull-left" id="navbar-collapse">
<ul class="nav navbar-nav">
<li class="active" ><a href="#" id="index">头部导航</a></li>
</ul>
{% for menu in request.top_menu %}
<ul class="nav navbar-nav">
<li {% ifequal menu.status True %}class="active" {% endifequal %}>
<a href="{{ menu.url }}" id="{{ menu.code }}">{{ menu.name | default_if_none:"" }}</a>
</li>
</ul>
{% endfor %}
</div>
{% if request.user.is_authenticated %}
<div class="navbar-custom-menu">

View File

@@ -18,9 +18,9 @@
<div class="col-sm-3">
<input class="form-control" name="name" type="text"/>
</div>
<label class="col-sm-2 control-label">代码</label>
<label class="col-sm-2 control-label">编号</label>
<div class="col-sm-3">
<input class="form-control" name="code" type="text"/>
<input class="form-control" name="number" type="text"/>
</div>
</div>
<div class="form-group has-feedback">
@@ -43,7 +43,12 @@
<div class="col-sm-8">
<input class="form-control" name="url" type="text" />
</div>
</div>
<div class="form-group has-feedback">
<label class="col-sm-2 control-label">代码</label>
<div class="col-sm-8">
<input class="form-control" name="code" type="text"/>
</div>
</div>
</fieldset>
</div>

View File

@@ -18,9 +18,9 @@
<div class="col-sm-3">
<input class="form-control" name="name" type="text" value="{{ menu.name }}"/>
</div>
<label class="col-sm-2 control-label">代码</label>
<label class="col-sm-2 control-label">编号</label>
<div class="col-sm-3">
<input class="form-control" name="code" type="text" value="{{ menu.code }}"/>
<input class="form-control" name="number" type="text" value="{{ menu.number }}"/>
</div>
</div>
<div class="form-group has-feedback">
@@ -32,6 +32,7 @@
<div class="col-sm-3">
<select class="form-control select2" name="parent">
<option value="{{ menu.parent.id }}">{{ menu.parent.name }}</option>
<option value=""> </option>
{% for parent_menu in menu_all %}
<option value={{ parent_menu.id }}> {{ parent_menu.name }} </option>
{% endfor %}
@@ -44,6 +45,12 @@
<input class="form-control" name="url" type="text" value="{{ menu.url | default:'' }}"/>
</div>
</div>
<div class="form-group has-feedback">
<label class="col-sm-2 control-label">代码</label>
<div class="col-sm-8">
<input class="form-control" name="code" type="text" value="{{ menu.code | default:'' }}"/>
</div>
</div>
</fieldset>
</div>
<div class="box-footer ">

View File

@@ -60,7 +60,13 @@
<script src="{% static 'plugins/datatables/jquery.dataTables.min.js' %}"></script>
<script src="{% static 'plugins/datatables/dataTables.const.js' %}"></script>
<script src="{% static 'js/plugins/layer/layer.js' %}"></script>
<script type="text/javascript">
$(function () {
$('#SYSTEM-RBAC').addClass('active');
$('#SYSTEM-RBAC-ROLE').addClass('active');
});
</script>
<script type="text/javascript">
var oDataTable = null;
$(function () {
@@ -142,8 +148,114 @@
oDataTable.ajax.reload();
}
});
}
}
//checkbox全选
$("#checkAll").on("click", function () {
if ($(this).prop("checked") === true) {
$("input[name='checkList']").prop("checked", $(this).prop("checked"));
$('#example tbody tr').addClass('selected');
} else {
$("input[name='checkList']").prop("checked", false);
$('#example tbody tr').removeClass('selected');
}
});
//批量删除
$("#btnDelete").click(function () {
if ($("input[name='checkList']:checked").length == 0) {
layer.msg("请选择要删除的记录");
return;
}
var arrId = new Array();
$("input[name='checkList']:checked").each(function () {
//alert($(this).val());
arrId.push($(this).val());
});
sId = arrId.join(',');
layer.alert('确定删除吗?', {
title: '提示'
, icon: 3 //0:感叹号 1对号 2差号 3问号 4小锁 5哭脸 6笑脸
, time: 0 //不自动关闭
, btn: ['YES', 'NO']
, yes: function (index) {
layer.close(index);
$.ajax({
type: "POST",
url: "{% url 'system:rbac-role-delete' %}",
data: {"id": sId, csrfmiddlewaretoken: '{{ csrf_token }}'},
cache: false,
success: function (msg) {
if (msg.result) {
layer.alert("操作成功", {icon: 1});
oDataTable.ajax.reload();
} else {
//alert(msg.message);
layer.alert("操作失败", {icon: 2});
}
return;
}
});
}
});
});
//删除单个数据
function doDelete(id) {
layer.alert('确定删除吗?', {
title: '提示'
, icon: 3 //0:感叹号 1对号 2差号 3问号 4小锁 5哭脸 6笑脸
, time: 0 //不自动关闭
, btn: ['YES', 'NO']
, yes: function (index) {
layer.close(index);
$.ajax({
type: "POST",
url: "{% url 'system:rbac-role-delete' %}",
data: {"id": id, csrfmiddlewaretoken: '{{ csrf_token }}'},
cache: false,
success: function (msg) {
if (msg.result) {
layer.alert('删除成功', {icon: 1});
oDataTable.ajax.reload();
} else {
//alert(msg.message);
layer.alert('删除失败', {icon: 2});
}
return;
}
});
}
});
}
//关联用户
function doUpdateUser(id) {
layer.open({
type: 2,
title: '绑定用户',
shadeClose: false,
maxmin: true,
area: ['800px', '600px'],
content: ["{% url 'system:rbac-role-role2user' %}" + '?id=' + id, 'no'],
});
}
//关联菜单
function doUpdateMenu(id) {
layer.open({
type: 2,
title: '权限分配',
shadeClose: false,
maxmin: true,
area: ['600px', '480px'],
content: ["{% url 'system:rbac-role-role2menu' %}" + '?id=' + id, 'no'],
});
}
</script>
{% endblock %}

View File

@@ -0,0 +1,179 @@
{% extends "base-layer.html" %} {% load static %}
{% block css %}
<link rel="stylesheet" href="{% static 'plugins/zTree/css/metroStyle/metroStyle.css' %}" type="text/css">
<link rel="stylesheet" href="{% static 'plugins/zTree/css/zTreeStyle/zTreeStyle.css' %}" type="text/css">
<link rel="stylesheet" href="{% static 'plugins/zTree/css/demo.css' %}" type="text/css">
{% endblock %}
{% block main %}
<style type="text/css">
.ztree li span.button.switch.level0 {
visibility: hidden;
width: 1px;
}
.ztree li ul.level0 {
padding: 0;
background: none;
}
</style>
<div class="box box-danger">
<div class="box-body">
<form class="form-horizontal" id="addTreeForm" action="" method="post">
{% csrf_token %}
<!-- 注释1页面实例是由Role2MenuView视图返回的同时传递了上下文role,这里使用role.id时用来提交POST请求时向后台传递的id-->
<input type="hidden" name='id' value="{{ role.id }}"/>
<input type="hidden" name="tree" id="tree" value=""/>
<div class="box-body">
<div class="row">
<div class="col-xs-5">
<div class="row span7 text-center ">
<label class="control-label"><h5>所有菜单</h5></label>
</div>
<div style="zTreeDemoBackground:left">
<ul id="left_tree" class="ztree"></ul>
</div>
</div>
<div class="col-xs-2">
<br><br><br><br><br><br>
<div class="text-center">
<button type="button" id="btnSave" class="btn btn-info margin-right ">生成</button>
</div>
<div class="text-center text-gray margin-top-5">{{ role.name }}权限</div>
</div>
<div class="col-xs-5">
<div class="row span7 text-center">
<label class="control-label"><h5>已选菜单</h5></label>
</div>
<ul id="right_tree" class="ztree"></ul>
</div>
</div>
</div>
</form>
</div>
</div>
{% endblock %}
{% block javascripts %}
<script type="text/javascript" src="{% static 'plugins/zTree/js/jquery.ztree.core.js' %}"></script>
<script type="text/javascript" src="{% static 'plugins/zTree/js/jquery.ztree.excheck.js' %}"></script>
<script type="text/javascript">
$(document).ready(function () {
var zTree;
var demoIframe;
var left_tree_setting = {
view: {
dblClickExpand: false,
showLine: true,
selectedMulti: true
},
check: {
enable: true,
//chkboxType : { "Y" : "", "N" : "" }
},
data: {
key: {
name: "name",
//title:"title",
},
simpleData: {
enable: true,
idKey: "id",
pIdKey: "parent",
rootPId: ""
},
}
};
var right_tree_setting = {
view: {
dblClickExpand: false,
showLine: true,
selectedMulti: true
},
check: {
enable: false,
//chkboxType : { "Y" : "", "N" : "" }
},
data: {
key: {
name: "name",
//title:"title",
},
simpleData: {
enable: true,
idKey: "id",
pIdKey: "parent",
rootPId: ""
},
}
};
$.ajax({
type: "GET",
url: "{% url 'system:rbac-role-role2menu_list' %}",
cache: false,
success: function (msg) {
layer.close();
var t = $("#left_tree");
t = $.fn.zTree.init(t, left_tree_setting, msg.data);
var treeObj = $.fn.zTree.getZTreeObj("left_tree");
treeObj.expandAll(true);
return;
}
});
$.ajax({
type: "GET",
url: "{% url 'system:rbac-role-role2menu_list' %}",
data: {"id":{{role.id}}},
cache: false,
success: function (msg) {
layer.close();
var t = $("#right_tree");
t = $.fn.zTree.init(t, right_tree_setting, msg.data);
var treeObj = $.fn.zTree.getZTreeObj("right_tree");
treeObj.expandAll(true);
return;
}
});
$("#btnSave").click(function () {
var treeObj = $.fn.zTree.getZTreeObj("left_tree");
var nodes = treeObj.getCheckedNodes(true);
$("#tree").val(JSON.stringify(nodes));
var data = $("#addTreeForm").serialize();
$.ajax({
type: $("#addTreeForm").attr('method'),
url: "{% url 'system:rbac-role-role2menu' %}",
data: data,
cache: false,
beforeSend: function () {
this.layerIndex = layer.load(1, {
shade: [0.1, '#fff']
});
},
success: function (msg) {
if (msg.result) {
layer.alert('操作成功', {icon: 1}, function (index) {
parent.layer.closeAll();
});
} else {
//alert(msg.message);
layer.alert('操作失败', {icon: 2});
}
return;
}
});
});
});
</script>
{% endblock %}

View File

@@ -0,0 +1,105 @@
{% extends 'base-layer.html' %}
{% load staticfiles %}
{% block css %}
<link rel="stylesheet" href="{% static 'plugins/select2/select2.min.css' %}">
{% endblock %}
{% block main %}
<div class="box box-danger">
<form class="form-horizontal" id="selectUsersForm" action="" method="post">
{% csrf_token %}
<input type="hidden" name='id' value="{{ role.id }}"/>
<div class="box-body">
<div class="row">
<div class="col-xs-5">
<label class="control-label">可选用户:</label>
<select name="from" id="multiselect" class="form-control" size="18" multiple="multiple">
{% for item in un_add_users %}
<option value="{{ item.id }}">{{ item.name }}({{ item.username }})</option>
{% endfor %}
</select>
</div>
<div class="col-xs-2">
<br><br><br><br><br><br>
<button type="button" id="multiselect_rightAll" class="btn btn-block"><i
class="glyphicon glyphicon-forward"></i></button>
<button type="button" id="multiselect_rightSelected" class="btn btn-block"><i
class="glyphicon glyphicon-chevron-right"></i></button>
<button type="button" id="multiselect_leftSelected" class="btn btn-block"><i
class="glyphicon glyphicon-chevron-left"></i></button>
<button type="button" id="multiselect_leftAll" class="btn btn-block"><i
class="glyphicon glyphicon-backward"></i></button>
</div>
<div class="col-xs-5">
<label class="control-label">{{ role.name }}-已绑定用户:</label>
<select name="to" id="multiselect_to" class="form-control" size="18" multiple="multiple">
{% for item in added_users %}
<option value="{{ item.id }}">{{ item.name }}({{ item.username }})</option>
{% endfor %}
</select>
</div>
</div>
<div class="row">
<div class="col-xs-12 margin-top-5">
<p class="text-maroon">*注意一个用户可以添加到多个角色中,继承多个角色的权限</p>
</div>
</div>
</div>
<div class="box-footer ">
<div class="row span7 text-center ">
<button type="button" id="btnCancel" class="btn btn-default margin-right ">重置</button>
<button type="button" id="btnSave" class="btn btn-info margin-right ">保存</button>
</div>
</div>
</form>
</div>
{% endblock %}
{% block javascripts %}
<script src="{% static 'plugins/select/multiselect.min.js' %}"></script>
<script type="text/javascript">
$(document).ready(function () {
//初始化多选列表
$('#multiselect').multiselect({
search: {
left: '<input type="text" class="form-control" placeholder="Search..." />',
right: '<input type="text" class="form-control" placeholder="Search..." />',
},
fireSearch: function (value) {
return value.length > 3;
}
});
});
$("#btnSave").click(function () {
$('#multiselect_to option').prop('selected', true);
var data = $("#selectUsersForm").serialize();
console.log(data);
$.ajax({
type: $("#selectUsersForm").attr('method'),
url: "{% url 'system:rbac-role-role2user' %}",
data: data,
cache: false,
success: function (msg) {
if (msg.result) {
layer.alert('操作成功!', {icon: 1}, function (index) {
parent.layer.closeAll();
});
} else {
//alert(msg.message);
layer.alert('操作失败', {icon: 2});
}
return;
}
});
});
/*点取消刷新新页面*/
$("#btnCancel").click(function () {
window.location.reload();
});
</script>
{% endblock %}

View File

@@ -57,6 +57,13 @@
<script src="{% static 'plugins/datatables/dataTables.const.js' %}"></script>
<script src="{% static 'js/plugins/layer/layer.js' %}"></script>
<script type="text/javascript">
$(function () {
$('#SYSTEM-BASIC').addClass('active');
$('#SYSTEM-BASIC-STRUCTURE').addClass('active');
});
</script>
<script type="text/javascript">
var oDataTable = null;
$(function () {

View File

@@ -4,14 +4,87 @@
{% block content %}
<div class="pad margin no-print">
<div class="callout callout-info" style="margin-bottom: 0!important;">
<h4><i class="fa fa-info-circle"></i>系统管理:</h4>
系统管理模块包含系统权限管理和系统设置系统权限管理可实现基于角色组的权限管理可根据角色组权限动态生成URL导航菜单
</div>
</div>
<!-- Main content -->
<section class="content">
系统管理首页system_indexcontent是页面定义的主要区域
头部和底部内容以及导航栏都是通过模板继承的之后的所有
功能前端页面都是在content内进行编辑
</section>
<section class="invoice">
<div class="row">
<div class="col-xs-12">
<h2 class="page-header">
<i class="fa fa-github"></i> RBAC权限管理历史版本
</h2>
</div>
<!-- /.col -->
</div>
<div class="row">
<div class="col-xs-12 table-responsive">
<table class="table table-striped">
<thead>
<tr>
<th>编号</th>
<th>TAG</th>
<th>发布日期</th>
<th>TAG地址</th>
<th>Commit</th>
</tr>
</thead>
<tbody>
<tr>
<td>1</td>
<td>v1.19</td>
<td>2018-11-16</td>
<td>https://github.com/RobbieHan/sandboxMP/tree/v1.19</td>
<td>system config</td>
</tr>
<tr>
<td>2</td>
<td>v1.18</td>
<td>2018-11-16</td>
<td>https://github.com/RobbieHan/sandboxMP/tree/v1.18</td>
<td>rbac config</td>
</tr>
<tr>
<td>3</td>
<td>v1.17</td>
<td>2018-11-14</td>
<td>https://github.com/RobbieHan/sandboxMP/tree/v1.17</td>
<td>role2menu</td>
</tr>
<tr>
<td>4</td>
<td>v1.16</td>
<td>2018-11-14</td>
<td>https://github.com/RobbieHan/sandboxMP/tree/v1.17</td>
<td>role2user</td>
</tr>
</tbody>
</table>
</div>
<!-- /.col -->
</div>
<!-- /.row -->
<div class="row">
<!-- accepted payments column -->
<div class="col-xs-12">
<p class="lead">其他信息</p>
<p class="text-muted well well-sm no-shadow" style="margin-top: 10px;">
<strong>权限管理开发文档获取地址知识星球</strong> https://t.zsxq.com/a6IqBMr (微信中打开链接)<br>
<strong>知识星球快捷入口</strong>微信公众号搜索[知识星球]关注后发送52824366获取星球连接<br>
<strong>知乎专栏SandBox</strong>https://zhuanlan.zhihu.com/sandbox <br>
<strong>轻量级办公管理系统项目开源地址</strong>https://github.com/RobbieHan/gistandard <br>
</p>
</div>
<!-- /.col -->
</div>
</section>
<!-- /.content -->
<div class="clearfix"></div>
{% endblock %}

View File

@@ -88,6 +88,14 @@
<script src="{% static 'plugins/datatables/dataTables.const.js' %}"></script>
<script src="{% static 'js/plugins/layer/layer.js' %}"></script>
<script type="text/javascript">
$(function () {
$('#SYSTEM-BASIC').addClass('active');
$('#SYSTEM-BASIC-USER').addClass('active');
});
</script>
<script type="text/javascript">
var oDataTable = null;
$(function () {