Skip to content

Commit 4e62da1

Browse files
authored
Add release note export script (#15109)
1 parent f1632e0 commit 4e62da1

File tree

2 files changed

+145
-3
lines changed

2 files changed

+145
-3
lines changed

scripts/export_release_notes.py

Lines changed: 139 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,139 @@
1+
#!/usr/bin/env python3
2+
3+
# Copyright 2025 Google LLC
4+
#
5+
# Licensed under the Apache License, Version 2.0 (the "License");
6+
# you may not use this file except in compliance with the License.
7+
# You may obtain a copy of the License at
8+
#
9+
# http://www.apache.org/licenses/LICENSE-2.0
10+
#
11+
# Unless required by applicable law or agreed to in writing, software
12+
# distributed under the License is distributed on an "AS IS" BASIS,
13+
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
14+
# See the License for the specific language governing permissions and
15+
# limitations under the License.
16+
17+
"""Creates release notes files."""
18+
19+
import argparse
20+
import os
21+
import subprocess
22+
import sys
23+
24+
25+
def main():
26+
changelog_location = find_changelog_location()
27+
28+
parser = argparse.ArgumentParser(description='Create release notes files.')
29+
parser.add_argument(
30+
'--version', '-v', required=True, help='Specify the release number.'
31+
)
32+
parser.add_argument('--date', help='Specify the date.')
33+
parser.add_argument(
34+
'--repo',
35+
'-r',
36+
required=True,
37+
help='The absolute path to the root of the repo containing changelogs.',
38+
)
39+
parser.add_argument(
40+
'products',
41+
help=(
42+
'The products to create changelogs for, separated by a comma (no'
43+
' space).'
44+
),
45+
)
46+
args = parser.parse_args()
47+
48+
# Check all inputs are valid product names
49+
products = args.products.split(',')
50+
product_paths = product_relative_locations()
51+
for i, product in enumerate(products):
52+
if product_paths[product] is None:
53+
print('Unknown product ' + product, file=sys.stderr)
54+
sys.exit(-1)
55+
56+
created_files = []
57+
repo = args.repo
58+
for i, product in enumerate(products):
59+
changelog = ''
60+
if product == 'Firestore' or product == 'Crashlytics':
61+
changelog = product + '/CHANGELOG.md'
62+
else:
63+
changelog = 'Firebase' + product + '/CHANGELOG.md'
64+
result = subprocess.run(
65+
[
66+
'python3',
67+
'scripts/make_release_notes.py',
68+
changelog,
69+
'-r',
70+
'firebase/firebase-ios-sdk',
71+
],
72+
cwd=repo,
73+
capture_output=True,
74+
text=True,
75+
check=True,
76+
)
77+
generated_note = result.stdout
78+
target_path = (
79+
changelog_location
80+
+ product_paths[product]
81+
+ '-m'
82+
+ args.version
83+
+ '.md'
84+
)
85+
with open(target_path, 'w') as file:
86+
file.write(generated_note)
87+
created_files.append(target_path)
88+
89+
output = '\n'.join(created_files)
90+
print(output)
91+
92+
93+
def find_changelog_location():
94+
wd = os.getcwd()
95+
google3_index = wd.rfind('google3')
96+
if google3_index == -1:
97+
print('This script must be invoked from a SrcFS volume', file=sys.stderr)
98+
sys.exit(-1)
99+
google3_root = wd[: google3_index + len('google3')]
100+
changelog_relative = (
101+
'/third_party/devsite/firebase/en/docs/ios/_ios-release-notes/'
102+
)
103+
changelog_absolute = google3_root + changelog_relative
104+
return changelog_absolute
105+
106+
107+
def product_relative_locations():
108+
module_names = [
109+
'ABTesting',
110+
'AI',
111+
# Note: Analytics is generated separately.
112+
'AppCheck',
113+
'Auth',
114+
'Core',
115+
'Crashlytics',
116+
'Database',
117+
'Firestore',
118+
'Functions',
119+
'Installations',
120+
'Messaging',
121+
'Storage',
122+
'RemoteConfig',
123+
# Note: Data Connect must be generated manually.
124+
]
125+
# Most products follow the format Product/_product(-version.md)
126+
relative_paths = {}
127+
for index, name in enumerate(module_names):
128+
path = name + '/_' + name.lower()
129+
relative_paths[name] = path
130+
131+
# There are a few exceptions
132+
relative_paths['AppDistribution'] = 'AppDistribution/_appdist'
133+
relative_paths['InAppMessaging'] = 'InAppMessaging/_fiam'
134+
relative_paths['Performance'] = 'Performance/_perf'
135+
return relative_paths
136+
137+
138+
if __name__ == '__main__':
139+
main()

scripts/make_release_notes.py

Lines changed: 6 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -51,10 +51,9 @@
5151

5252

5353
def main():
54-
local_repo = find_local_repo()
5554

5655
parser = argparse.ArgumentParser(description='Create release notes.')
57-
parser.add_argument('--repo', '-r', default=local_repo,
56+
parser.add_argument('--repo', '-r',
5857
help='Specify which GitHub repo is local.')
5958
parser.add_argument('--only', metavar='VERSION',
6059
help='Convert only a specific version')
@@ -64,6 +63,10 @@ def main():
6463
help='The CHANGELOG.md file to parse')
6564
args = parser.parse_args()
6665

66+
repo = args.repo
67+
if repo is None:
68+
repo = find_local_repo()
69+
6770
if args.all:
6871
text = read_file(args.changelog)
6972
else:
@@ -73,7 +76,7 @@ def main():
7376
if not args.all:
7477
product = PRODUCTS.get(args.changelog)
7578

76-
renderer = Renderer(args.repo, product)
79+
renderer = Renderer(repo, product)
7780
translator = Translator(renderer)
7881

7982
result = translator.translate(text)

0 commit comments

Comments
 (0)