Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/mysql/67.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Mysql Django admin-模型对超级用户可见,而不是对职员用户可见_Mysql_Django_Django Admin_Migration - Fatal编程技术网

Mysql Django admin-模型对超级用户可见,而不是对职员用户可见

Mysql Django admin-模型对超级用户可见,而不是对职员用户可见,mysql,django,django-admin,migration,Mysql,Django,Django Admin,Migration,我知道syncdb和makemigrations,但我们仅限于在生产环境中这样做 我们最近在生产中创建了两个表。正如预期的那样,任何用户都无法在管理员上看到表。 在此之后,我们在生产sql上手动执行了以下两个查询(我在本地运行了迁移,并执行了showcreatetablequery以获取原始sql) django\u内容类型 INSERT INTO django_content_type(name, app_label, model) values ('linked_urls',"urls",

我知道
syncdb
makemigrations
,但我们仅限于在生产环境中这样做

我们最近在生产中创建了两个表。正如预期的那样,任何用户都无法在管理员上看到表。
在此之后,我们在生产sql上手动执行了以下两个查询(我在本地运行了迁移,并执行了
showcreatetable
query以获取原始sql)

django\u内容类型

INSERT INTO django_content_type(name, app_label, model) 
values ('linked_urls',"urls", 'linked_urls');
授权权限

INSERT INTO auth_permission (name, content_type_id, codename) 
values 
('Can add linked_urls Table', (SELECT id FROM django_content_type where model='linked_urls' limit 1) ,'add_linked_urls'),
('Can change linked_urls Table', (SELECT id FROM django_content_type where model='linked_urls' limit 1) ,'change_linked_urls'),
('Can delete linked_urls Table', (SELECT id FROM django_content_type where model='linked_urls' limit 1) ,'delete_linked_urls');
现在,此模型在超级用户下可见,并且可以授予员工用户访问权限,但员工用户看不到它。
是否有需要在其中输入的表格条目

或者,没有syncdb迁移,还有其他方法可以解决这个问题吗

我们最近在生产中创建了两个表

我可以用两种方式读你在那里写的东西

第一种方法:使用SQL语句创建表,Django中没有相应的模型。如果是这样的话,再多的篡改内容类型和权限也不会让Django突然使用这些表。您需要为表创建模型。也许他们会,但他们需要存在

第二种方法:Django中的相应模型确实存在,您只需手动为它们创建表,所以这不是问题。在这种情况下,我要做的是运行以下代码,代码后面跟着解释:

来自django.contrib.contenttypes.management导入更新\u contenttypes
从django.apps将应用作为配置的应用导入
从django.contrib.auth.management导入创建权限
对于已配置的应用程序中的应用程序。获取应用程序配置()
更新内容类型(app,interactive=True,verbosity=0)
对于已配置的应用程序中的应用程序。获取应用程序配置()
创建权限(应用程序,详细度=0)

上面的代码实际上是执行Django在运行迁移后执行的工作。当迁移发生时,Django只是根据需要创建表,然后当迁移完成时,它调用
update\u contenttypes
,扫描与项目中定义的模型相关联的表,并将需要添加的内容添加到
Django\u content\u type
表中。然后调用
create\u permissions
来更新
auth\u permissions
,添加/更改/删除需要添加的权限。我已经使用上面的代码强制提前创建权限。例如,如果我进行了数据迁移,创建了需要引用新权限的组,这将非常有用。

因此,我终于找到了一个解决方案。我在django上进行了大量调试,显然下面的函数(位于
django.contrib.auth.backends
)负责提供权限

def _get_permissions(self, user_obj, obj, from_name):
    """
    Returns the permissions of `user_obj` from `from_name`. `from_name` can
    be either "group" or "user" to return permissions from
    `_get_group_permissions` or `_get_user_permissions` respectively.
    """
    if not user_obj.is_active or user_obj.is_anonymous() or obj is not None:
        return set()

    perm_cache_name = '_%s_perm_cache' % from_name
    if not hasattr(user_obj, perm_cache_name):
        if user_obj.is_superuser:
            perms = Permission.objects.all()
        else:
            perms = getattr(self, '_get_%s_permissions' % from_name)(user_obj)
        perms = perms.values_list('content_type__app_label', 'codename').order_by()
        setattr(user_obj, perm_cache_name, set("%s.%s" % (ct, name) for ct, name in perms))
    return getattr(user_obj, perm_cache_name)
那么问题出在哪里?

此查询中存在的问题:

INSERT INTO django_content_type(name, app_label, model) 
values ('linked_urls',"urls", 'linked_urls');
最初看起来不错,但实际执行的查询是:

--# notice the caps case here - it looked so trivial, i didn't even bothered to look into it untill i realised what was happening internally
INSERT INTO django_content_type(name, app_label, model) 
values ('Linked_Urls',"urls", 'Linked_Urls'); 
因此,django在内部执行
migrate
时,确保所有内容都以小写形式进行迁移,这就是问题所在


我执行了一个单独的查询来降低所有先前插入的大小写,瞧

可能有一个员工用户组。你授予它权限了吗?是的,还有很多不属于任何组的独立人员用户!然后我建议创建用户组
staff
,并将其分配给所有staff用户。我不喜欢这个,但应该也可以通过一个SQL命令来处理分配。只是尝试了一下,创建了一个组,让模型访问该组…分配给用户。仍然没有运气。看不到表。这是您提到的第二种方式。现在,我的问题是我没有在prod/pre-prod上运行shell的权限。是否有任何原始的
sql
内容可以传递给DBA以执行查询并完成任务?您没有这个问题。任何Django管理命令都可以通过从python代码中调用
Django.core.management.call\u命令来运行。如果创建一个包装该函数的视图,则可以运行任何需要的操作。但是,如果有疑问,也可以从python调用命令,并使用库调用Django视图。是的,这两种方法都允许您运行迁移。