繁体   English   中英

如何使用Django从Oracle 11g中的不同架构访问表?

[英]How to access tables from a different schema in oracle 11g using django?

我在oracle 11g中有一个名为mi_abc的用户。 用户在数据库中没有任何表,但是可以访问另一个模式sch_abc中的所有表。 当我从mi_abc的sch_abc模式运行来自sqldeveloper的普通选择查询时,它工作得很好,但是当我使用django时,总是出现错误:

django.db.utils.DatabaseError: ORA-00942: table or view does not exist

我试图设置db_table = sch_abc.tableName,还设置了db_table = tableName,但是两者都给了我同样的错误。 任何线索如何解决这个问题?

跟踪:-

Traceback (most recent call last):
  File "C:\xxx\xxx\xxx\xxx\xxx\xxx\xxxx\lib\site-packages\django\core\handlers\exception.py", line 41, in inner
    response = get_response(request)
  File "C:\xxx\xxx\xxxx\xxxx\xxxx\Python\Python37\lib\site-packages\django\utils\deprecation.py", line 142, in __call__
    response = self.process_response(request, response)
  File "C:\xxxx\xxxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\contrib\sessions\middleware.py", line 58, in process_response
    request.session.save()
  File "C:\xxx\xxxx\xxxx\xxxx\xxxxx\Python\Python37\lib\site-packages\django\contrib\sessions\backends\db.py", line 81, in save
    return self.create()
  File "C:\xxxx\xxxxx\xxxx\xxxx\xxxxx\Python\Python37\lib\site-packages\django\contrib\sessions\backends\db.py", line 50, in create
    self._session_key = self._get_new_session_key()
  File "C:\xxxx\xxxxx\xxxxx\xxxxx\xxxx\Python\Python37\lib\site-packages\django\contrib\sessions\backends\base.py", line 164, in _get_new_session_key
    if not self.exists(session_key):
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\contrib\sessions\backends\db.py", line 46, in exists
    return self.model.objects.filter(session_key=session_key).exists()
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\models\query.py", line 673, in exists
    return self.query.has_results(using=self.db)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\models\sql\query.py", line 517, in has_results
    return compiler.has_results()
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\models\sql\compiler.py", line 858, in has_results
    return bool(self.execute_sql(SINGLE))
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\models\sql\compiler.py", line 899, in execute_sql
    raise original_exception
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\models\sql\compiler.py", line 889, in execute_sql
    cursor.execute(sql, params)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\backends\utils.py", line 79, in execute
    return super(CursorDebugWrapper, self).execute(sql, params)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\backends\utils.py", line 64, in execute
    return self.cursor.execute(sql, params)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\utils.py", line 94, in __exit__
    six.reraise(dj_exc_type, dj_exc_value, traceback)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\utils\six.py", line 685, in reraise
    raise value.with_traceback(tb)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\backends\utils.py", line 64, in execute
    return self.cursor.execute(sql, params)
  File "C:\xxx\xxx\xxx\xxx\xxx\Python\Python37\lib\site-packages\django\db\backends\oracle\base.py", line 497, in execute
    return self.cursor.execute(query, self._param_generator(params))
django.db.utils.DatabaseError: ORA-00942: table or view does not exist

好吧,我解决了这个问题,让我告诉您,在Django中没有直接的方法。 我的应用程序存在的问题是,我正在使用django的认证功能以及会话处理功能。 所有这些表都是由django在初始迁移时直接创建的。 因此,在models.py文件中不存在它们,您只需添加模式名称并要求您的应用程序连接到该模式的表即可。

我最终要做的是,为实际上包含这些表的其他模式的所有表创建了私有同义词。 如果执行此操作,则无需在Django代码中进行任何更改。 您的应用程序将仅能正常工作,因为oracle会完成实际连接到正确表的工作。 您将仅在应用程序中调用该表,就好像它是您自己的一样。 这样,当django查找像django_session,auth_user等的表时,它像往常一样简单地查询它,并且oracle将其重定向到另一个模式中存在的实际表。

希望这对将来会遇到此问题的人们有所帮助。

这绝对不是官方支持,但是可以在Postgres中使用:

class Meta:
    managed = False
    db_table = 'schema\".\"table'

Postgres经过了反复试验,但您可能可以对Oracle做类似的事情。 这是因为Postgres引擎引用对象名称,而这会伪造引用机制。

更新:

进行一些挖掘之后,我发现了针对Oracle(针对Python 3进行了修改)的代码:

class Meta:
    db_table = '"SCHEMA"."TABLE_NAME"'

资料来源: https : //code.djangoproject.com/ticket/14136

除非您真的知道自己在做什么,否则我建议保持managed = False 祝好运!

您可以在执行命令之前设置所需的架构。 然后在处理查询集后返回到公共架构。

from django.db import connection
connection.set_schema(schema_name)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM