summaryrefslogblamecommitdiffstats
path: root/webapp/src/components/PermissionModuleEdit.vue
blob: 13a4b17a0f4bf3bcf302a6d5e5231c8c14109cf2 (plain) (tree)
1
2
3
4
5
6
7
8
9
10
11
12
13


         









                                       
                                                      

                                                  

         









                                        
                                                             

                                                        







                                                         
                     
              
              

            
                                         


































                                                                                                                
                                 



                             
                                           




                                                                                                                


                                         


                                      

                                                                         
                                









                                            

                                  

                                                                                                                                   
                                                            
                                                                                                 


                                         
                                                       
                                      

                                      


                                                                   

                             
                                         

                                  
                                                                    




                                                      
                                   

                              
                                                                                                                    
                                                            
                                                                                                 


                                         
                                                       
                                      

                                      


                                                                

                             
                                         


                                          





















                                                                         

                                   
                                      
                                                                              
                                                                        











                                                                                               
                                      
                                                                         
                                                                        
                                  
                                                      


                                             

                                                                                                

























                                                                                                                    

                                                                    



                               


                        




                       

                      

                              
                        
                             
                          


                                                                    

                     


                                                              














                                                                           

                                             
                             
                                                                        
                                                          


                                                          



                       
                                                                                  

                                            

                                                            
                                                            














                                                            






















                                                                                                              


                                                          
                   
                                                          






                                                                         


             






                                               
                         
                               


                                     

                                    
                                
                
                                     

                             
                                
         



              
                          





                                                                   






                    





                      



               
        
<i18n>
{
  "en": {
    "id": "ID",
    "name": "Name",
    "description": "Description",
    "groupdependent": "Groupdependent",
    "submit": "Submit",
    "role": "Role",
    "permissions": "Permissions",
    "groups": "Groups",
    "summary": "Summary",
    "roleName": "Role Name",
    "roleNameEmptyError": "Role Name can't be empty.",
    "recursiveMode": "Select Groups recursive",
    "roleSavedSuccess": "Role saved successfully."
  },
  "de": {
    "id": "ID",
    "name": "Name",
    "description": "Beschreibung",
    "groupdependent": "Gruppengebunden",
    "submit": "Einreichen",
    "role": "Rolle",
    "permissions": "Rechte",
    "groups": "Gruppen",
    "summary": "Zusammenfassung",
    "roleName": "Rollenname",
    "roleNameEmptyError": "Rollenname kann nicht leer sein.",
    "recursiveMode": "Gruppen rekursiv auswählen",
    "roleSavedSuccess": "Rolle erfolgreich gespeichert."
  }
}
</i18n>

<template>
  <v-dialog
    :value="$store.state.permissions.edit"
    @input="$store.commit('permissions/setEdit', $event)"
    max-width="800px"
    scrollable
    persistent
  >
    <v-card>
      <v-card-title class="dialog-title">
        <v-stepper v-model="step" horizontal  style="width: 100%; background: transparent;" class="elevation-3">
          <v-stepper-header>
            <v-stepper-step
              :complete="stepCompleted >= 1"
              step="1"
              :editable="stepCompleted >= 1"
              edit-icon="check"
            >
              {{ $t('role') }}
            </v-stepper-step>
            <v-divider></v-divider>
            <v-stepper-step
              :complete="stepCompleted >= 2"
              step="2"
              :editable="stepCompleted >= 2"
              edit-icon="check"
            >
              {{ $t('permissions') }}
            </v-stepper-step>
            <v-divider></v-divider>
            <v-stepper-step
              :complete="stepCompleted >= 3"
              step="3"
              :editable="stepCompleted >= 3"
              edit-icon="check"
            >
              {{ $t('groups') }}
            </v-stepper-step>
            <v-divider></v-divider>
            <v-stepper-step
              :complete="stepCompleted >= 4"
              step="4"
              :editable="stepCompleted >= 4"
              edit-icon="check"
            >
              {{ $t('summary') }}
            </v-stepper-step>
          </v-stepper-header>
        </v-stepper>
      </v-card-title>
      <v-card-text class="table-container">
        <v-form v-model="valid" ref="form" @submit.prevent="submit" lazy-validation>
          <v-stepper v-model="step" horizontal style="width: 100%; background: transparent" class="elevation-0">
            <v-stepper-items>

              <v-stepper-content step="1">
                <v-text-field
                  v-model="roleName"
                  :label="$t('roleName')"
                  prepend-icon="label"
                  class="info-input"
                  color="primary"
                  :rules="[() => !!roleName || $t('roleNameEmptyError')]"
                  ref="roleName"
                ></v-text-field>

                <v-textarea
                  v-model="roleDescr"
                  :label="$t('description')"
                  prepend-icon="description"
                  class="info-input"
                  color="primary"
                  rows="1"
                  auto-grow
               ></v-textarea>
              </v-stepper-content>

              <v-stepper-content step="2" class="stepper-padding-0">
                <component-search-table v-model="permissionsSelected" :headers="permissionHeaders" :items="permissions" select-all>
                  <template slot="items" slot-scope="props">
                    <tr :style="props.color" @click="props.data.selected = !props.data.selected">
                      <td>
                        <v-checkbox
                          color="primary"
                          v-model="props.data.selected"
                          hide-details
                        ></v-checkbox>
                      </td>
                      <td>{{ props.data.item.name }}</td>
                      <td>{{ props.data.item.descr }}</td>
                      <td>{{ props.data.item.groupdependent }}</td>
                    </tr>
                  </template>
                </component-search-table>
              </v-stepper-content>

              <v-stepper-content step="3" class="stepper-padding-0">
                <v-flex xs4 offset-xs4>
                  <v-switch
                    :label="$t('recursiveMode')"
                    :input-value="recursiveSwitch"
                    @change="recursiveSwitch = $event"
                    color="primary"
                  ></v-switch>
                </v-flex>
                <component-search-table v-model="groupsSelected" :headers="groupHeaders" :items="groups" select-all>
                  <template slot="items" slot-scope="props">
                    <tr :style="props.color" @click="props.data.selected = !props.data.selected">
                      <td>
                        <v-checkbox
                          color="primary"
                          v-model="props.data.selected"
                          hide-details
                        ></v-checkbox>
                      </td>
                      <td>{{ props.data.item.id }}</td>
                      <td>{{ props.data.item.name }}</td>
                      <td>{{ props.data.item.description }}</td>
                    </tr>
                  </template>
                </component-search-table>
              </v-stepper-content>

              <v-stepper-content step="4">
                <v-text-field
                  v-model="roleName"
                  :label="$t('roleName')"
                  prepend-icon="label"
                  class="info-input"
                  color="primary"
                  :rules="[() => !!roleName || $t('roleNameEmptyError')]"
                  ref="roleName"
                  disabled
                ></v-text-field>

                <v-textarea
                  v-model="roleDescr"
                  :label="$t('description')"
                  prepend-icon="description"
                  class="info-input"
                  color="primary"
                  rows="1"
                  auto-grow
                  disabled
               ></v-textarea>

                <v-layout row wrap>
                  <v-flex>
                    <v-list subheader>
                      <v-subheader inset>{{ $t('permissions') }}</v-subheader>
                      <v-divider class="list-header-margin"></v-divider>
                      <v-list-tile
                        v-for="permission in permissionsSelected"
                        :key="permission.id"
                      >
                        <v-list-tile-content>
                          <v-list-tile-title>{{ permission.name }}</v-list-tile-title>
                          <v-list-tile-sub-title>{{ permission.descr }}</v-list-tile-sub-title>
                        </v-list-tile-content>
                      </v-list-tile>
                    </v-list>
                  </v-flex>
                  <v-flex>
                    <v-list subheader>
                      <v-subheader inset>{{ $t('groups') }}</v-subheader>
                      <v-divider class="list-header-margin"></v-divider>
                      <v-list-tile
                        v-for="group in groupsSummary"
                        :key="group.id"
                      >
                        <v-list-tile-content>
                          <v-list-tile-title>{{ group.id }} {{ group.name }}</v-list-tile-title>
                          <v-list-tile-sub-title>{{ group.description }}</v-list-tile-sub-title>
                        </v-list-tile-content>
                      </v-list-tile>
                    </v-list>
                  </v-flex>
                </v-layout>
              </v-stepper-content>

            </v-stepper-items>
          </v-stepper>
        </v-form>
      </v-card-text>
      <v-divider></v-divider>
      <v-card-actions>
        <v-flex xl10 offset-xl1 lg12 text-xs-right>
          <v-btn flat @click.native="$store.commit('permissions/setEdit', false )">{{ $t('cancel') }}</v-btn>
          <v-btn color="primary" v-show="step == 1" @click.native="completeStepOne()">{{ $t('continue') }}</v-btn>
          <v-btn color="primary" v-show="step == 2" @click.native="completeStepTwo()">{{ $t('continue') }}</v-btn>
          <v-btn color="primary" v-show="step == 3" @click.native="completeStepThree()">{{ $t('continue') }}</v-btn>
          <v-btn class="success" v-show="step == 4" @click="submit" type="submit">{{ $t('submit') }}</v-btn>
        </v-flex>
      </v-card-actions>
    </v-card>
  </v-dialog>
</template>

<script>
import _arrayIncludes from 'lodash/_arrayIncludes'
import ComponentSearchTable from '@/components/ComponentSearchTable'

export default {
  name: 'PermissionModuleEdit',
  props: ['roleId'],
  components: {
    ComponentSearchTable
  },
  data () {
    return {
      valid: true,
      step: 1,
      stepCompleted: 0,
      permissions: [],
      groups: [],
      permissionsSelected: [],
      groupsSelected: [],
      groupsSummary: [],
      recursiveSwitch: false,
      permissionHeaders: [
        { text: this.$t('name'), value: 'name' },
        { text: this.$t('description'), value: 'descr' },
        { text: this.$t('groupdependent'), value: 'groupdependent' }
      ],
      groupHeaders: [
        { text: this.$t('id'), value: 'id' },
        { text: this.$t('name'), value: 'name' },
        { text: this.$t('description'), value: 'description' }
      ],
      roleName: '',
      roleDescr: ''
    }
  },
  methods: {
    submit (event) {
      if (this.$refs.form.validate()) {
        const filteredPermissions = this.permissionsSelected.map(x => x.id)
        const filteredGroups = this.groupsSelected.map(x => x.id)
        this.$http.post('/api/permissions/saveRole', {
          id: this.roleId,
          name: this.roleName,
          descr: this.roleDescr,
          permissions: filteredPermissions,
          groups: filteredGroups,
          recursiveMode: this.recursiveSwitch
        }).then(response => {
          this.$store.commit('newSnackbar', this.$t('roleSavedSuccess'))
          this.$store.dispatch('permissions/loadRoleData')
          this.$store.commit('permissions/setEdit', false)
        }).catch(error => {
          console.log(error)
        })
      }
    },
    loadRole (roleId) {
      this.$http('/api/permissions/getRoleById/' + this.roleId).then(response => {
        this.roleName = response.data.name
        this.roleDescr = response.data.descr
        this.permissionsSelected = response.data.permissions
        this.groupsSelected = response.data.groups
        this.recursiveSwitch = response.data.recursiveGroups
      })
    },
    completeStepOne () {
      if (this.roleName !== '') {
        this.step = 2
        this.stepCompleted = Math.max(1, this.stepCompleted)
      } else {
        this.$refs.form.validate()
      }
    },
    completeStepTwo () {
      this.step = 3
      this.stepCompleted = Math.max(2, this.stepCompleted)
    },
    completeStepThree () {
      if (this.recursiveSwitch === true) {
        var promises = []
        var childGroups = []
        var self = this
        // _arrayIncludes.js
        this.groupsSelected.forEach(function (group) {
          promises.push(self.$http('/api/groups/getGroup?all=true&id=' + group.id).then(response => {
            response.data.subgroups.forEach(function (subgroup) {
              if (!(_arrayIncludes(self.groupsSelected, subgroup) || _arrayIncludes(childGroups, subgroup))) {
                childGroups.push(subgroup)
              }
            })
          }))
        })

        Promise.all(promises).then(() => {
          console.log(JSON.stringify(this.groupsSelected))
          console.log(JSON.stringify(childGroups))
          this.groupsSummary = this.groupsSelected.concat(childGroups)
        })
      } else {
        this.groupsSummary = this.groupsSelected
      }
      this.step = 4
      this.stepCompleted = Math.max(3, this.stepCompleted)
    },
    loadGroups () {
      this.$http('/api/groups/getList').then(response => {
        this.groups = response.data
      })
    },
    loadPermissions () {
      this.$http('/api/permissions/getPermissionList').then(response => {
        this.permissions = response.data
      })
    }
  },
  computed: {
    edit: function () {
      return this.$store.state.permissions.edit
    }
  },
  watch: {
    edit: function (value) {
      if (value) {
        this.loadGroups()
        this.$refs.form.reset()
        this.permissionsSelected = []
        this.groupsSelected = []
        this.step = 1
        if (this.roleId !== 0) {
          this.loadRole(this.roleId)
          this.stepCompleted = 4
        } else {
          this.recursiveSwitch = true
          this.roleName = ''
          this.roleDescr = ''
          this.stepCompleted = 0
        }
      }
    }
  },
  created () {
    this.loadPermissions()
  }
}
</script>

<!-- Add "scoped" attribute to limit CSS to this component only -->
<style scoped>
.table-container {
  padding: 0;
  height: 700px;
}
.stepper-padding-0 {
  padding: 0;
}
.info-input {
  margin: 20px;
}
.list-header-margin {
  margin-bottom: 10px;
}
.dialog-title {
  padding: 0px;
  z-index: 1;
}
</style>