yiisoft / yii2

Yii 2: The Fast, Secure and Professional PHP Framework
http://www.yiiframework.com
BSD 3-Clause "New" or "Revised" License
14.23k stars 6.91k forks source link

Implicit conversion from data type char to varbinary(max) is not allowed #13680

Closed Schwoebel closed 6 years ago

Schwoebel commented 7 years ago

What steps will reproduce the problem?

    namespace app\commands;

    use app\rbac\IsYourSchoolRule;
    use yii;
    use yii\console\Controller;

    class RbacController extends Controller
    {

      public function actionInit()
      {
        $auth = Yii::$app->authManager;
        //Create our 4 Roles
        $admin = $auth->createRole('admin');
        $auth->add($admin);
        $principal = $auth->createRole('Lokal-Admin');
    $auth->add($principal);
    $unit_admin = $auth->createRole('Chef');
    $auth->add($unit_admin);
    $teacher = $auth->createRole('Personal');
    $auth->add($teacher);

    //Assign roles in their descending order to their parent
    $auth->addChild($admin, $principal);
    $auth->addChild($principal, $unit_admin);
    $auth->addChild($unit_admin, $teacher);

    /*
     * Initialize the Rule that restricts user-activity to only their assigned school
     */
    $rule = new IsYourSchoolRule;

    //create the permission that allows a person to toggle any students attendance
    $toggleAttendance = $auth->createPermission('toggleAttendance');
    $toggleAttendance->description = 'Ändra närvaro';
    $auth->add($toggleAttendance);
    //Give this permission to toggle ANY students attendance exclusively to the admin.
    $auth->addChild($principal, $toggleAttendance);

    // add the rule
    $auth->add($rule);
    //Create the permission that will use this RuleClass to check if the user is assigned to the same school as the student
    $toggleThisStudent = $auth->createPermission('toggleThisStudentsAttendance');
    $toggleThisStudent->description = 'Ändra elevens närvaro';
    $toggleThisStudent->ruleName = $rule->name;
    //Add the permission to the DB
    $auth->add($toggleThisStudent);
    //Add this permission as a child of the toggle-any-student permission to establish a relation between the two
    $auth->addChild($toggleAttendance, $toggleThisStudent);
    //Add the toggle-student-assigned-to-your-school rule to any teacher
    $auth->addChild($teacher, $toggleThisStudent);
    //So now we should be able to Toggle any student in our school if we are a teacher, group-leader, or principal as
    //long as they are assigned to a group that is in the same school as us.
    //But if the user has the role of admin they should be able to toggle the attendance of anyone, regardless of
    //school.

    /*
     * From here the process is a little less comment-y.  But it is following the same premise as explained in detail above.
     * For this project it breaks down like this;
     * 1.Create a broad-stroke rule.
     * 2.Add it to the auth manager
     * 3.Add it as a child of admin, since admin is the highest level of user.
     * 4. Initialize the new RULE
     * 5. add the RULE to the auth manager
     * 6. create a Permission, as more or less a "container" to hold the rule so the authmanager has something to check
     *  it against.  The auth manager can't simply check rules.  It only checks permissions
     * 7. add the description and rule name for the permission.
     * 8. add the permission to the auth manager
     * 9. add the permission to the broad-stroke permission as a CHILD permisssion
     * 10. add the permission that contains your rule to the lowest level role it should apply to.
     *   That way if that role is a child of another role it will apply to that one too.
     *
     * Rinse. Repeat until all of the rules in the app\rbac rolder have been added.
     */

    $createStudent = $auth->createPermission('addStudent');
    $createStudent->description = 'Lägg till elev';
    $auth->add($createStudent);
    $auth->addChild($admin, $createStudent);

    $createStudentForGroup = $auth->createPermission('addStudentToAssignedSchoolsGroups');
    $createStudentForGroup->description = "Create Student for a group in your school";
    $createStudentForGroup->ruleName = $rule->name;

    $auth->add($createStudentForGroup);

    $auth->addChild($createStudent, $createStudentForGroup);
    $auth->addChild($unit_admin, $createStudentForGroup);

    $moveStudent = $auth->createPermission('moveStudent');
    $moveStudent->description = "Move student between groups and/or schools";
    $auth->add($moveStudent);
    $auth->addChild($admin, $moveStudent);

    $moveStudentsBetweenGroupsInYourSchool = $auth->createPermission('moveStudentBetweenGroupsInTheSchoolYouAreAPartOf');
    $moveStudentsBetweenGroupsInYourSchool->description = 'Move Students betweeen groups in YOUR school';
    $moveStudentsBetweenGroupsInYourSchool->ruleName = $rule->name;

    $auth->add($moveStudentsBetweenGroupsInYourSchool);

    $auth->addChild($moveStudent, $moveStudentsBetweenGroupsInYourSchool);
    $auth->addChild($unit_admin, $moveStudentsBetweenGroupsInYourSchool);

    $editStudent = $auth->createPermission('editStudent');
    $editStudent->description = "Edit Students";
    $auth->add($editStudent);
    $auth->addChild($admin, $editStudent);

    $editStudentsInYourGroup = $auth->createPermission('editStudentsInYourSchoolsGroups');
    $editStudentsInYourGroup->description = 'Edit a Student that is in your schools groups';
    $editStudentsInYourGroup->ruleName = $rule->name;

    $auth->add($editStudentsInYourGroup);

    $auth->addChild($editStudent, $editStudentsInYourGroup);
    $auth->addChild($teacher, $editStudentsInYourGroup);

    $addTeachers = $auth->createPermission('addTeacher');
    $addTeachers->description = 'Lägg till lärare i grupp';
    $auth->add($addTeachers);
    $auth->addChild($admin, $addTeachers);

    $addTeacherToYourSchool = $auth->createPermission('addTeacherToYourOwnSchool');
    $addTeacherToYourSchool->description = 'Add a teacher to the school you are assigned to';
    $addTeacherToYourSchool->ruleName = $rule->name;

    $auth->add($addTeacherToYourSchool);

    $auth->addChild($addTeachers, $addTeacherToYourSchool);
    $auth->addChild($unit_admin, $addTeacherToYourSchool);

    $addGroups = $auth->createPermission('addGroup');
    $addGroups->description = 'Lägg till grupp i skola';
    $auth->add($addGroups);
    $auth->addChild($admin, $addGroups);

    $addGroupToYourSchool = $auth->createPermission('addGroupToYourSchool');
    $addGroupToYourSchool->description = "Add a group to the school you are assigned to";
    $addGroupToYourSchool->ruleName = $rule->name;

    $auth->add($addGroupToYourSchool);

    $auth->addChild($addGroups, $addGroupToYourSchool);
    $auth->addChild($principal, $addGroupToYourSchool);

    $addSchool = $auth->createPermission('addSchool');
    $addSchool->description = 'Lägg till skola';
    $auth->add($addSchool);
    $auth->addChild($admin, $addSchool);

    $addUsersWithChildRoles = $auth->createPermission('addUser');
    $addUsersWithChildRoles->description = "Add users with roles below yours";
    $auth->add($addUsersWithChildRoles);
    $auth->addChild($admin, $addUsersWithChildRoles);

    $editProfile = $auth->createPermission('editProfile');
    $editProfile->description = 'Edit User Profile';
    $auth->add($editProfile);
    $auth->addChild($admin, $editProfile);

    // add the rule
    $rule = new \app\rbac\EditProfileRule;
    $auth->add($rule);

    // add the "updateOwnPost" permission and associate the rule with it.
    $updateOwnProfile = $auth->createPermission('editOwnProfile');
    $updateOwnProfile ->description = 'edit Own Profile';
    $updateOwnProfile ->ruleName = $rule->name;
    $auth->add($updateOwnProfile );

    // "updateOwnProfle" will be used from "updateProfile"
    $auth->addChild($updateOwnProfile, $editProfile);

    // allow "teacher" to update their own profile
    $auth->addChild($teacher, $updateOwnProfile);

      }

     }

Then run rbac/init

What is the expected result?

The file should populate the rbac DB with rule and role data

What do you get instead?

C:\inetpub\wwwroot\kungalvs>php yii rbac/init Exception 'yii\db\Exception' with message     'SQLSTATE[42000]: [Microsoft][ODBC Driver 11 for SQL Server][SQL Server]Implicit conversion from data type char to varbinary(max) is not allowed. Use the CONVERT function to run this query.The SQL being executed was: INSERT INTO [auth_item] ([name], [type], [description], [rule_name], [data], [created_at], [updated_at]) VALUES ('admin', 1, NULL, NULL, NULL, 1488272331, 1488272331)'

in C:\inetpub\wwwroot\kungalvs\vendor\yiisoft\yii2\db\Schema.php:636

Error Info:
Array
(
    [0] => 42000
    [1] => 257
    [2] => [Microsoft][ODBC Driver 11 for SQL Server][SQL Server]Implicit conversion from data     type char to varbinary(max) is not allowed. Use the CONVERT function to run this query.
    )

Additional info

Q A
Yii version 2.0.11.2
PHP version 5.6.24
Operating system DB Driver 11 Microsoft Windows Server 2012 R2
OkyTrilupito commented 6 years ago

image

please help me.. this is still not work only on rbac.. I'm use version 2.0.13 with yii2-admin extension and SQL Server 2017.

please tell me step by step to solve it.

Implicit conversion from data type char to varbinary(max) is not allowed. Use the CONVERT function to run this query. The SQL being executed was: INSERT INTO [auth_item] ([name], [type], [description], [rule_name], [data], [created_at], [updated_at]) VALUES ('/auth/assignment/view', 2, NULL, NULL, NULL, 1509737632, 1509737632)

samdark commented 6 years ago

Please create new issue.