• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

htdangkhoa / google-ads / 15898762526

26 Jun 2025 09:55AM UTC coverage: 96.235% (-3.8%) from 100.0%
15898762526

Pull #172

github

web-flow
Merge 124a63d3b into 5f3c9e417
Pull Request #172: Bugfix/cannot use with google auth library v10

65 of 65 branches covered (100.0%)

Branch coverage included in aggregate %.

10 of 26 new or added lines in 1 file covered. (38.46%)

344 of 360 relevant lines covered (95.56%)

13.17 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

80.72
/src/utils.ts
1
import {
4✔
2
  credentials,
3
  OAuth2Client,
4
  ServiceError,
5
  Metadata,
6
} from '@grpc/grpc-js';
7

8
import { GoogleAdsFailure } from './generated/google/ads/googleads/v20/errors/errors.js';
4✔
9
import { MutateGoogleAdsResponse } from './generated/google/ads/googleads/v20/services/google_ads_service.js';
10
import { FAILURE_KEY } from './constants.js';
4✔
11

12
export const getCredentials = (authClient: OAuth2Client) => {
4✔
13
  const ssl = credentials.createSsl();
12✔
14

15
  const callCredentials = credentials.createFromMetadataGenerator(
12✔
16
    ({ service_url }, callback) => {
12✔
17
      (authClient as any)
48✔
18
        .getRequestHeaders(service_url)
48✔
19
        .then((requestHeaders) => {
48✔
NEW
20
          const metadata = new Metadata();
×
21

NEW
22
          let headers = requestHeaders;
×
23

NEW
24
          if (globalThis.Headers || global.Headers) {
×
NEW
25
            const headerEntries = Object.fromEntries(headers);
×
NEW
26
            headers = Object.entries(headerEntries).reduce(
×
NEW
27
              (acc, [key, value]) => {
×
NEW
28
                acc[key] = value;
×
NEW
29
                return acc;
×
NEW
30
              },
×
NEW
31
              {} as Record<string, string>,
×
NEW
32
            );
×
NEW
33
          }
×
34

NEW
35
          Object.entries<string>(headers).forEach(([key, value]) => {
×
NEW
36
            metadata.set(key, value);
×
NEW
37
          });
×
38

NEW
39
          callback(null, metadata);
×
40
        })
48✔
41
        .catch((err) => callback(err));
48✔
42
    },
48✔
43
  );
12✔
44

45
  const channelCredentials = credentials.combineChannelCredentials(
12✔
46
    ssl,
12✔
47
    callCredentials,
12✔
48
  );
12✔
49

50
  return channelCredentials;
12✔
51
};
12✔
52

53
export const decodeGoogleAdsFailureBuffer = (buffer: Buffer) => {
4✔
54
  const input = new Uint8Array(buffer);
8✔
55

56
  return GoogleAdsFailure.decode(input);
8✔
57
};
8✔
58

59
export const getGoogleAdsError = (
4✔
60
  error: Error | ServiceError,
8✔
61
): GoogleAdsFailure | Error => {
8✔
62
  // @ts-expect-error
63
  if (typeof error.metadata?.internalRepr?.get?.(FAILURE_KEY) === 'undefined') {
8✔
64
    return error;
4✔
65
  }
4✔
66

67
  // @ts-expect-error
68
  const [buffer] = error.metadata.internalRepr.get(FAILURE_KEY);
4✔
69

70
  return decodeGoogleAdsFailureBuffer(buffer);
4✔
71
};
4✔
72

73
export const decodePartialFailureError = (
4✔
74
  response: MutateGoogleAdsResponse,
20✔
75
) => {
20✔
76
  if (!response.partial_failure_error) return response;
20✔
77

78
  const { details } = response.partial_failure_error;
16✔
79

80
  if (!details) return response;
20✔
81

82
  const { value } =
12✔
83
    details.find((detail) =>
12✔
84
      detail.type_url?.includes('errors.GoogleAdsFailure'),
8✔
85
    ) ?? {};
20✔
86

87
  if (!value) return response;
20✔
88

89
  const buffer = Buffer.from(value);
4✔
90

91
  return {
4✔
92
    ...response,
4✔
93
    partial_failure_error: decodeGoogleAdsFailureBuffer(buffer),
4✔
94
  };
4✔
95
};
4✔
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2026 Coveralls, Inc