为什么我的环境变量加载两次,第一次使用正确的值,第二次使用空值

问题描述 投票:0回答:1

在 Playwright api 测试期间,我无法读取测试中指定环境的 API_URL 值。

我的全局设置:

import * as dotenv from 'dotenv';
import fs from 'fs/promises';
import path from 'path';

interface User {
  username: string;
  password: string;
  cis: string;
  debitCard: string;
}

interface BankAccount {
  accountNumber: string;
  title: string;
}

interface TransferTitles {
  [key: string]: string;
}

export let CONFIG: {
  BASE_URL: string;
  API_URL: string;
  ENV: string;
  USERS: User[];
  BANK_ACCOUNTS: BankAccount[];
  COMMON_TRANSFER_TITLES: TransferTitles;
} = {
  BASE_URL: '',
  API_URL: '',
  ENV: '',

};

async function globalSetup(): Promise<void> {
  const environment = process.env.ENV || 'uat';
  console.log(`Loading environment: ${environment}`);
  const envPath = path.resolve(__dirname, `../../.env.${environment}`);
  console.log(`Loading .env file from: ${envPath}`);
  dotenv.config({ path: envPath, override: true });
  console.log(`Loaded BASE_URL from .env: ${process.env.BASE_URL}`);
  console.log(`Loaded API_URL from .env: ${process.env.API_URL}`);

  CONFIG = {
    BASE_URL: process.env.BASE_URL ?? '[NOT SET]',,
    API_URL: process.env.API_URL ?? '[NOT SET]',
    ENV: environment,
    COMMON_TRANSFER_TITLES: {},
    USERS: [],
    BANK_ACCOUNTS: [],
  };

  try {
    const commonDataPath = path.resolve(__dirname, './COMMON/commonData.json');
    const commonData = await fs.readFile(commonDataPath, 'utf8');
    const parsedCommonData = JSON.parse(commonData);
    CONFIG.COMMON_TRANSFER_TITLES = parsedCommonData.transferTitles;
    console.log('Common data loaded successfully.');
  } catch (error) {
    console.error('Error loading common data:', error);
    throw new Error('Failed to load common data');
  }

  try {
    const testDataPath = path.resolve(__dirname, `./${environment}/testData-${environment}.json`);
    const testData = await fs.readFile(testDataPath, 'utf8');
    const parsedTestData = JSON.parse(testData);
    CONFIG.USERS = parsedTestData.users;
    CONFIG.BANK_ACCOUNTS = parsedTestData.bankAccounts;
    console.log(`${environment} data loaded successfully.`);
  } catch (error) {
    console.error(`Error loading ${environment} data:`, error);
    throw new Error(`Failed to load ${environment} data`);
  }

  console.log('Global setup completed. Configuration and test data loaded.');
  console.log(`Final BASE_URL in CONFIG: ${CONFIG.BASE_URL}`);
  console.log(`Final API_URL in CONFIG: ${CONFIG.API_URL}`);

  global.CONFIG = CONFIG;
}

export default globalSetup;

我的 utils 中的 api_requests 文件

import { CONFIG } from './global-setup';
import { APIRequestContext } from '@playwright/test';

const headersUnblock = {
  'sim-state': 'UNKNOWN',
  'device-flag-vpn': 'true',
  'os-type': 'iOS',
};

console.log('CONFIG.API_URL at top level:', CONFIG.API_URL);

export const putUnblockRequest = async (request: APIRequestContext): Promise<any> => {
  console.log('CONFIG.API_URL inside function:', CONFIG.API_URL);
  const baseApiUrl = CONFIG.API_URL;
  const path = '/my/path';
  const url = `${baseApiUrl}${path}`;
  console.log('Full URL:', url);
  const response = await request.fetch(url, {
    method: 'PUT',
    headers: headersUnblock,
  });
  console.log('Response:', response);
  return response;
};

我的 api.spec.ts 文件:


import { putUnblockRequest } from '../../src/utils/api_requests';
import { expect, request as pwRequest, test } from '@playwright/test';
import { CONFIG } from '../../src/utils/global-setup';
console.log('CONFIG after import:', CONFIG);

test.describe('API Tests', () => {
  let request: any;

  test.beforeAll(async ({ playwright }) => {
    request = await pwRequest.newContext({
      extraHTTPHeaders: {},
    });
  });

  test.afterAll(async () => {
    await request.dispose();
  });

  

  test.only('PUT request to unblock all channels', async () => {
    console.log('CONFIG.API_URL BEFORE calling putUnblockRequest:', CONFIG.API_URL);
    const response = await putUnblockRequest(request);
    expect(response.status()).toBe(204);
  });
});

为什么我无法执行API测试? - 我的 api_requests 网址 我尝试了一切 atm,当我进入函数时,我丢失了 CONFIG.API_URL,当尝试 console.log('CONFIG.API_URL at top level:', CONFIG.API_URL);

时,它可用。
 const baseApiUrl = CONFIG.API_URL;
  const path = '/my/path';
  const url = `${baseApiUrl}${path}`;

始终只是/我的/路径

javascript typescript environment-variables playwright
1个回答
0
投票

看起来问题是您正在

CONFIG
函数中重新分配导出的值
globalSetup

CONFIG = {
  BASE_URL: process.env.BASE_URL ?? '[NOT SET]',,
  API_URL: process.env.API_URL ?? '[NOT SET]',
  ENV: environment,
  COMMON_TRANSFER_TITLES: {},
  USERS: [],
  BANK_ACCOUNTS: [],
};

虽然此语句更改

CONFIG
globalSetup
的值,但它不会覆盖您要导入到规范文件中的 cached 导出的
CONFIG

也许只是将配置放入其自己的模块中,不要尝试通过

globalSetup
钩子初始化它。例如:

// config.ts

// Call dotenv.load, read values from data files, etc. ...

export default {
  API_URL: process.env.API_URL,
  BASE_URL: process.env.BASE_URL,
  ENV: process.env.ENV,
  USERS: ...,
  BANK_ACCOUNTS: ...,
  COMMON_TRANSFER_TITLES: ...,
};

或者,Playwright 允许您在 playwright.config.ts 中指定自定义的 optionsparameters,并将其注入到每个测试用例中。 IMO,这是配置测试的最优雅的方式。

© www.soinside.com 2019 - 2024. All rights reserved.