没有超级用户角色就无法创建扩展

Rud*_*lah 46 django postgresql postgis postgresql-9.1

我正在尝试在Django中运行单元测试,它会创建一个新的数据库.数据库有postgis扩展,当我经常创建数据库时,我使用"CREATE ExTENSION postgis".

但是,当我运行测试时,它会给我以下错误:

$ ./manage.py test
Creating test database for alias 'default'...
Got an error creating the test database: database "test_project" already exists

Type 'yes' if you would like to try deleting the test database 'test_project', or 'no' to cancel: yes
Destroying old test database 'default'...
DatabaseError: permission denied to create extension "postgis"
HINT:  Must be superuser to create this extension.
Run Code Online (Sandbox Code Playgroud)

用户已经具有Create DB权限,我在Ubuntu 12.04上使用Postgis 2.0使用PostgreSQL 9.1.

Rud*_*lah 90

关于postgis的Django文档提供了一些有关设置用户权限的信息.

在最坏的情况下,您可以创建一个新的超级用户:

$ createuser --superuser <user_name>
Run Code Online (Sandbox Code Playgroud)

或改变现有用户的角色:

postgres# ALTER ROLE <user_name> SUPERUSER;
Run Code Online (Sandbox Code Playgroud)

  • 您的应用程序不应以超级用户身份运行。我已经为这个问题提供了解决方案。 (5认同)
  • @HarryMoreno 我很久以前在一家机构工作时写了这个答案,该机构的数据库与网络应用程序位于同一服务器上,并且会在营销活动结束时被拆除,并且不会触及其他用户数据。不过,我总体上同意,我从事的所有其他项目都拥有适当的用户权限(但如果您只是在本地测试,为什么不使用超级用户:P) (2认同)

Ari*_*iel 39

我找到的最简单的方法是:

su postgres
psql
alter role user_name superuser;
#then create the extension as the user in a different screen
alter role user_name nosuperuser;
Run Code Online (Sandbox Code Playgroud)

基本上在短时间内为用户提供超级用户权限,并创建扩展.然后撤销超级用户权限.

您还可以使用\connect user_name该用户并直接从postgres用户创建扩展.

  • 这是有道理的,让用户保留超级用户权限是没有意义的,可以减少攻击面。我喜欢! (3认同)
  • 然而攻击可能在那短暂的瞬间存在 (3认同)

Har*_*eno 11

另一种解决这个问题的方法是在django docs中提出的

$ psql <db name>
> CREATE EXTENSION postgis;
Run Code Online (Sandbox Code Playgroud)

您可以以超级用户身份登录数据库并创建一次扩展.然后,您的api的db用户可以使用该扩展.当django执行CREATE EXTENSION IF NOT EXISTS postgispostgres时不会抛出.

如果您在迁移doublecheck时看到错误,则在正确的数据库中创建扩展,这是一个示例sesssion

$ psql
=> \l            - list databases
=> \c <db name>  - connect to django db
=> create extension postgis;
Run Code Online (Sandbox Code Playgroud)

如果您看到表格,则可以验证是否已安装扩展程序 spatial_ref_sys

=> \dt
                   List of relations
 Schema |            Name            | Type  |  Owner
--------+----------------------------+-------+----------
 public | spatial_ref_sys            | table | postgres
Run Code Online (Sandbox Code Playgroud)

对于测试,我建议在本地开发数据库上运行它们并授予用户超级用户权限 > ALTER ROLE <user_name> SUPERUSER;

  • 我不同意,stackoverflow 应该是有组织的,有用还不足以给出答案。要么这是不可能的,应该更新问题(标题),要么您的答案(以及所有其他答案)应该转移到一个单独的问题(用户权限和扩展的良好实践)。因为我不知道答案所以无法决定,但目前的状态看起来一团糟 (2认同)
  • 我不同意@cglacet,所有其他选项实际上包括使应用程序用户成为超级用户,实际上此页面上没有不需要超级用户权限的解决方案。至少使用此解决方案,您不会摆弄应用程序用户的权限并在将来打开危险的后门。 (2认同)

小智 10

您也可以安装postgistemplate1所有新创建的数据库默认继承的数据库模板。

$ psql -U postgres -d template1 -c "CREATE EXTENSION postgis;"
Run Code Online (Sandbox Code Playgroud)

从此点创建的所有新数据库都将postgis安装扩展,包括 Django 的测试数据库,除非它们在创建数据库时指定了不同的模板。

如果postgis不需要安装到所有新创建的数据库中,可以创建一个新模板,安装postgis在其中,然后让 Django 在创建测试数据库时使用该模板。

$ createdb template_postgis;  # create a new database
$ psql -U postgres -c "UPDATE pg_database SET datistemplate = TRUE WHERE datname = 'template_postgis';"  # make it a template
$ psql -U postgres -d template_postgis -c "CREATE EXTENSION postgis;"  # install postgis in it
Run Code Online (Sandbox Code Playgroud)

然后在 Django 设置中:

...
DATABASES = {
    'default': {
        ...
        'TEST': {
            'TEMPLATE': 'template_postgis',
        },
    },
}
Run Code Online (Sandbox Code Playgroud)


Pet*_*sen 9

CREATE从 Postgres 13 开始,某些模块/扩展被认为是“可信的”,并且可以由对当前数据库具有特权的非超级用户安装。

\n

可信模块有:btree_gin、btree_gist、citext、cube、dict_int、fuzzystrmatch、hstore、intarray、is、lo、ltree、pgcrypto、pg_trgm、seg、tablefunc、tcn、tsm_system_rows、tsm_system_time、unaccent、uuid-ossp

\n

要检查给定模块是否符合条件,请访问https://www.postgresql.org/docs/13/contrib.html并选择有问题的模块。如果它被认为是“可信的”,该页面将包含以下句子:

\n
\n

该模块被视为\xe2\x80\x9ctrusted\xe2\x80\x9d,即可以由对CREATE当前数据库具有权限的非超级用户安装。

\n
\n


COR*_*ian 6

在不委派超级用户权限的情况下执行此操作的一种安全方法是访问我们正在其中使用具有超级用户角色的用户(例如 postgres)执行查询的数据库。

$ sudo -u postgres psql <db_name>

<db_name>#= CREATE EXTENSION IF NOT EXISTS <your-extension>;
Run Code Online (Sandbox Code Playgroud)

这样您就不会暴露安全性,并且可以相信数据库中的扩展。

GL