2017-05-29 185 views
0

我有一個函數返回一個查詢,該查詢可以通過給定的帳戶ID獲取«電子郵件的新優先級»。 首先它爲該帳戶選擇一個域名,然後爲它選擇一個數據結構。 而且一切都應該是正確的國際海事組織,但不是在這個時候:SQLAlchemy正在生成語法錯誤的SQL,我不明白如何解決它。下面是樣本:SQLAlchemy生成的SQL不正確

def unprocessed_by_account_id(account_id: str): 
    account_domain = select(
     [tables.organizations.c.organization_id]).select_from(
     tables.accounts.join(
      tables.email_addresses, 
      tables.accounts.c.account_id == tables.email_addresses.c.email_address, 
     ).join(tables.organizations) 
    ).where(
     tables.accounts.c.account_id == account_id, 
    ) 
    domain_with_subdomains = concat('%', account_domain) 
    fields = [ 
     tables.users.c.first_name, 

     … 
     tables.priorities.c.name, 
    ] 
    fromclause = tables.users.join(
     … 
    ).join(tables.organizations) 
    whereclause = and_(
     … 
     tables.organizations.c.organization_id.notlike(
      domain_with_subdomains), 
    ) 
    stmt = select(fields).select_from(fromclause).where(whereclause) 

    return stmt 

print(unprocessed_by_account_id(‘foo’)) 

因此產生:

SELECT 
    users.first_name, 
    … 
    priorities.name 
FROM (SELECT organizations.organization_id AS organization_id 
     FROM accounts 
     JOIN email_addresses 
      ON accounts.account_id = email_addresses.email_address 
     JOIN organizations 
      ON organizations.organization_id = email_addresses.organization_id 
     WHERE accounts.account_id = :account_id_1), users 
    JOIN 
    … 
    JOIN organizations 
    ON organizations.organization_id = email_addresses.organization_id 
WHERE emails.account_id = :account_id_2 AND 
     priorities_new_emails.status = :status_1 AND 
     organizations.organization_id NOT LIKE 
     concat(:concat_1, (SELECT organizations.organization_id 
         FROM accounts 
          JOIN email_addresses ON accounts.account_id = 
                email_addresses.email_address 
          JOIN organizations 
          ON organizations.organization_id = 
           email_addresses.organization_id 
         WHERE accounts.account_id = :account_id_1)) 

但第一

(SELECT organizations.organization_id AS organization_id 
     FROM accounts 
     JOIN email_addresses 
      ON accounts.account_id = email_addresses.email_address 
     JOIN organizations 
      ON organizations.organization_id = email_addresses.organization_id 
     WHERE accounts.account_id = :account_id_1) 

是多餘的位置,併產生

[2017-05-29 23:49:51] [42601] ERROR: subquery in FROM must have an alias 
[2017-05-29 23:49:51] Hint: For example, FROM (SELECT ...) [AS] foo. 
[2017-05-29 23:49:51] Position: 245 

我試圖用account_domain = account_domain.cte() ,但沒有運氣,excep如預期那樣子查詢去到WITH條款。 我也試過with_only_columns,根本沒有任何效果。 我認爲鍊金術正在添加這個聲明,因爲它在WHERE子句中看到它,並認爲沒有它,過濾將導致錯誤,但我不確定。 另外我必須提到的是,與以前版本的代碼相比,聲明幾乎相同,除了沒有concat(‘%’, account_domain)notlike!=。 另外我嘗試在這裏和那裏插入alias,但是沒有成功。如果我手動刪除select中的第一條語句是純SQL,那麼我會收到預期的結果。

任何幫助表示讚賞,謝謝。

+0

你能發佈聲明型號請。 –

回答

1

如果您使用子查詢作爲一個值,你需要聲明它as_scalar()

domain_with_subdomains = concat('%', account_domain.as_scalar())