cloudy-salesforce 0.2.0__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- cloudy_salesforce-0.2.0/.cloudy_config.example +42 -0
- cloudy_salesforce-0.2.0/.cursor/skills/ship-pr/SKILL.md +83 -0
- cloudy_salesforce-0.2.0/.github/ISSUE_TEMPLATE/bug.yml +56 -0
- cloudy_salesforce-0.2.0/.github/ISSUE_TEMPLATE/feature.yml +34 -0
- cloudy_salesforce-0.2.0/.github/workflows/ci.yml +21 -0
- cloudy_salesforce-0.2.0/.github/workflows/publish.yml +22 -0
- cloudy_salesforce-0.2.0/.gitignore +166 -0
- cloudy_salesforce-0.2.0/CHANGELOG.md +40 -0
- cloudy_salesforce-0.2.0/CONTRIBUTING.md +38 -0
- cloudy_salesforce-0.2.0/LICENSE +21 -0
- cloudy_salesforce-0.2.0/PKG-INFO +242 -0
- cloudy_salesforce-0.2.0/README.md +212 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/__init__.py +33 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/client/__init__.py +13 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/client/auth.py +171 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/client/config.py +166 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/client/salesforceclient.py +201 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/collections/__init__.py +35 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/collections/crud_operations.py +353 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/collections/return_functions.py +60 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/collections/serialize.py +89 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/collections/types.py +13 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/exceptions.py +28 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/generator/__init__.py +5 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/generator/cli.py +112 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/generator/generator.py +238 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/generator/templates/sobject.jinja2 +27 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/py.typed +0 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/query/__init__.py +9 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/query/query.py +107 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/query/return_functions.py +5 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/sobjects/__init__.py +13 -0
- cloudy_salesforce-0.2.0/cloudy_salesforce/sobjects/sobject.py +203 -0
- cloudy_salesforce-0.2.0/examples/generated/Account.py +20 -0
- cloudy_salesforce-0.2.0/examples/generated/Opportunity.py +19 -0
- cloudy_salesforce-0.2.0/examples/generated/__init__.py +2 -0
- cloudy_salesforce-0.2.0/pyproject.toml +63 -0
- cloudy_salesforce-0.2.0/requirements.txt +2 -0
- cloudy_salesforce-0.2.0/tests/__init__.py +0 -0
- cloudy_salesforce-0.2.0/tests/conftest.py +34 -0
- cloudy_salesforce-0.2.0/tests/fixtures/account_opportunity_fields.py +51 -0
- cloudy_salesforce-0.2.0/tests/test_auth.py +174 -0
- cloudy_salesforce-0.2.0/tests/test_cli.py +253 -0
- cloudy_salesforce-0.2.0/tests/test_client.py +183 -0
- cloudy_salesforce-0.2.0/tests/test_collections.py +270 -0
- cloudy_salesforce-0.2.0/tests/test_examples_generated.py +82 -0
- cloudy_salesforce-0.2.0/tests/test_generator.py +256 -0
- cloudy_salesforce-0.2.0/tests/test_parse_sobject.py +183 -0
- cloudy_salesforce-0.2.0/tests/test_query.py +147 -0
|
@@ -0,0 +1,42 @@
|
|
|
1
|
+
{
|
|
2
|
+
"auth": {
|
|
3
|
+
"default_alias": "prod",
|
|
4
|
+
"aliases": {
|
|
5
|
+
"prod": {
|
|
6
|
+
"type": "basic",
|
|
7
|
+
"login_url": "https://login.salesforce.com",
|
|
8
|
+
"credentials": {
|
|
9
|
+
"username": "SF_USERNAME",
|
|
10
|
+
"password": "SF_PASSWORD",
|
|
11
|
+
"security_token": "SF_SECURITY_TOKEN"
|
|
12
|
+
}
|
|
13
|
+
},
|
|
14
|
+
"sandbox": {
|
|
15
|
+
"type": "basic",
|
|
16
|
+
"sandbox": true,
|
|
17
|
+
"credentials": {
|
|
18
|
+
"username": "SF_USERNAME",
|
|
19
|
+
"password": "SF_PASSWORD",
|
|
20
|
+
"security_token": "SF_SECURITY_TOKEN"
|
|
21
|
+
}
|
|
22
|
+
},
|
|
23
|
+
"jwt": {
|
|
24
|
+
"type": "jwt",
|
|
25
|
+
"login_url": "https://login.salesforce.com",
|
|
26
|
+
"credentials": {
|
|
27
|
+
"client_id": "SF_CLIENT_ID",
|
|
28
|
+
"username": "SF_USERNAME",
|
|
29
|
+
"private_key": "SF_PRIVATE_KEY"
|
|
30
|
+
}
|
|
31
|
+
},
|
|
32
|
+
"session": {
|
|
33
|
+
"type": "session",
|
|
34
|
+
"credentials": {
|
|
35
|
+
"access_token": "SF_ACCESS_TOKEN",
|
|
36
|
+
"instance_url": "SF_INSTANCE_URL"
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
},
|
|
41
|
+
"sobjects": ["Account", "Contact", "Opportunity"]
|
|
42
|
+
}
|
|
@@ -0,0 +1,83 @@
|
|
|
1
|
+
---
|
|
2
|
+
name: ship-pr
|
|
3
|
+
description: >-
|
|
4
|
+
Create a pull request, review and fix issues, merge it, then switch back to
|
|
5
|
+
main and pull. Use when the user asks to create a PR and merge, ship, close
|
|
6
|
+
and merge, review then merge, or run this project's ship-pr process.
|
|
7
|
+
---
|
|
8
|
+
|
|
9
|
+
# Ship PR
|
|
10
|
+
|
|
11
|
+
End-to-end ship: open a PR, review/fix, merge, return to `main`.
|
|
12
|
+
|
|
13
|
+
Never merge unless this skill was invoked or the user explicitly asked to merge in this conversation. Opening a PR alone is not permission to merge.
|
|
14
|
+
|
|
15
|
+
## 1. Create the PR
|
|
16
|
+
|
|
17
|
+
Use `gh` for all GitHub work. Do not use TodoWrite or Task for this step.
|
|
18
|
+
|
|
19
|
+
In parallel:
|
|
20
|
+
|
|
21
|
+
- `git status`
|
|
22
|
+
- `git diff` and `git diff --cached`
|
|
23
|
+
- whether the branch tracks a remote and is up to date
|
|
24
|
+
- `git log` and `git diff [base]...HEAD` (full history since the branch diverged)
|
|
25
|
+
|
|
26
|
+
Then, in order:
|
|
27
|
+
|
|
28
|
+
1. Create a branch if needed.
|
|
29
|
+
2. Push with `-u` if the branch is not on the remote.
|
|
30
|
+
3. Create the PR:
|
|
31
|
+
|
|
32
|
+
```bash
|
|
33
|
+
gh pr create --title "the pr title" --body "$(cat <<'EOF'
|
|
34
|
+
## Summary
|
|
35
|
+
<1-3 bullet points>
|
|
36
|
+
|
|
37
|
+
## Test plan
|
|
38
|
+
[Checklist of TODOs for testing the pull request...]
|
|
39
|
+
|
|
40
|
+
EOF
|
|
41
|
+
)"
|
|
42
|
+
```
|
|
43
|
+
|
|
44
|
+
Return the PR URL.
|
|
45
|
+
|
|
46
|
+
Do not update git config. Do not force-push to main/master.
|
|
47
|
+
|
|
48
|
+
## 2. Review and fix
|
|
49
|
+
|
|
50
|
+
Review the PR diff yourself (not only CI).
|
|
51
|
+
|
|
52
|
+
Fix real bugs, missing tests, and incorrect docs on the feature branch. Commit and push those fixes. Do not commit secrets.
|
|
53
|
+
|
|
54
|
+
Leave leftover non-blocking work as GitHub issues. Do not pile follow-ups onto `main`.
|
|
55
|
+
|
|
56
|
+
## 3. Merge
|
|
57
|
+
|
|
58
|
+
Confirm the PR is mergeable and CI is green (or the user accepted failing checks).
|
|
59
|
+
|
|
60
|
+
```bash
|
|
61
|
+
gh pr merge <N> --merge --delete-branch
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
Use a merge commit unless the repo or human prefers squash/rebase.
|
|
65
|
+
|
|
66
|
+
## 4. Return to main
|
|
67
|
+
|
|
68
|
+
Always finish on `main` with a current tree:
|
|
69
|
+
|
|
70
|
+
```bash
|
|
71
|
+
git checkout main
|
|
72
|
+
git pull
|
|
73
|
+
git fetch --prune
|
|
74
|
+
```
|
|
75
|
+
|
|
76
|
+
Delete the local feature branch if it still exists.
|
|
77
|
+
|
|
78
|
+
## Do not
|
|
79
|
+
|
|
80
|
+
- Merge as part of merely opening a PR
|
|
81
|
+
- Leave the session on the feature branch after merge
|
|
82
|
+
- Commit directly to `main`
|
|
83
|
+
- Start the next issue unless asked
|
|
@@ -0,0 +1,56 @@
|
|
|
1
|
+
name: Bug report
|
|
2
|
+
description: Report something that is broken or incorrect
|
|
3
|
+
title: "[Bug]: "
|
|
4
|
+
labels:
|
|
5
|
+
- bug
|
|
6
|
+
body:
|
|
7
|
+
- type: markdown
|
|
8
|
+
attributes:
|
|
9
|
+
value: |
|
|
10
|
+
Thanks for reporting a bug. Please include enough detail to reproduce the issue.
|
|
11
|
+
|
|
12
|
+
- type: textarea
|
|
13
|
+
id: description
|
|
14
|
+
attributes:
|
|
15
|
+
label: Description
|
|
16
|
+
description: What went wrong?
|
|
17
|
+
placeholder: A clear description of the bug.
|
|
18
|
+
validations:
|
|
19
|
+
required: true
|
|
20
|
+
|
|
21
|
+
- type: textarea
|
|
22
|
+
id: reproduction
|
|
23
|
+
attributes:
|
|
24
|
+
label: Steps to reproduce
|
|
25
|
+
description: Minimal steps or code snippet to trigger the issue.
|
|
26
|
+
placeholder: |
|
|
27
|
+
1. ...
|
|
28
|
+
2. ...
|
|
29
|
+
validations:
|
|
30
|
+
required: true
|
|
31
|
+
|
|
32
|
+
- type: textarea
|
|
33
|
+
id: expected
|
|
34
|
+
attributes:
|
|
35
|
+
label: Expected behavior
|
|
36
|
+
description: What did you expect to happen instead?
|
|
37
|
+
validations:
|
|
38
|
+
required: true
|
|
39
|
+
|
|
40
|
+
- type: input
|
|
41
|
+
id: python-version
|
|
42
|
+
attributes:
|
|
43
|
+
label: Python version
|
|
44
|
+
description: e.g. 3.12.4
|
|
45
|
+
placeholder: "3.12"
|
|
46
|
+
validations:
|
|
47
|
+
required: true
|
|
48
|
+
|
|
49
|
+
- type: input
|
|
50
|
+
id: package-version
|
|
51
|
+
attributes:
|
|
52
|
+
label: cloudy-salesforce version
|
|
53
|
+
description: Output of `pip show cloudy-salesforce` or git commit if installed from source.
|
|
54
|
+
placeholder: "0.1.0"
|
|
55
|
+
validations:
|
|
56
|
+
required: true
|
|
@@ -0,0 +1,34 @@
|
|
|
1
|
+
name: Feature request
|
|
2
|
+
description: Suggest an improvement or new capability
|
|
3
|
+
title: "[Feature]: "
|
|
4
|
+
labels:
|
|
5
|
+
- enhancement
|
|
6
|
+
body:
|
|
7
|
+
- type: markdown
|
|
8
|
+
attributes:
|
|
9
|
+
value: |
|
|
10
|
+
Describe the problem you are trying to solve and how you would like cloudy-salesforce to help.
|
|
11
|
+
|
|
12
|
+
- type: textarea
|
|
13
|
+
id: problem
|
|
14
|
+
attributes:
|
|
15
|
+
label: Problem
|
|
16
|
+
description: What pain point or gap does this address?
|
|
17
|
+
placeholder: I want to ...
|
|
18
|
+
validations:
|
|
19
|
+
required: true
|
|
20
|
+
|
|
21
|
+
- type: textarea
|
|
22
|
+
id: proposed-solution
|
|
23
|
+
attributes:
|
|
24
|
+
label: Proposed solution
|
|
25
|
+
description: How should cloudy-salesforce behave or what API would you expect?
|
|
26
|
+
validations:
|
|
27
|
+
required: true
|
|
28
|
+
|
|
29
|
+
- type: textarea
|
|
30
|
+
id: alternatives
|
|
31
|
+
attributes:
|
|
32
|
+
label: Alternatives considered
|
|
33
|
+
description: Other approaches, workarounds, or libraries you considered.
|
|
34
|
+
placeholder: Optional but helpful.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
name: CI
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
push:
|
|
5
|
+
pull_request:
|
|
6
|
+
|
|
7
|
+
jobs:
|
|
8
|
+
test:
|
|
9
|
+
runs-on: ubuntu-latest
|
|
10
|
+
strategy:
|
|
11
|
+
matrix:
|
|
12
|
+
python-version: ["3.10", "3.11", "3.12", "3.13"]
|
|
13
|
+
steps:
|
|
14
|
+
- uses: actions/checkout@v4
|
|
15
|
+
- uses: actions/setup-python@v5
|
|
16
|
+
with:
|
|
17
|
+
python-version: ${{ matrix.python-version }}
|
|
18
|
+
- run: pip install -e ".[dev]"
|
|
19
|
+
- run: ruff check cloudy_salesforce tests
|
|
20
|
+
- run: mypy cloudy_salesforce
|
|
21
|
+
- run: pytest
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
name: Publish
|
|
2
|
+
|
|
3
|
+
on:
|
|
4
|
+
release:
|
|
5
|
+
types: [published]
|
|
6
|
+
|
|
7
|
+
permissions:
|
|
8
|
+
id-token: write
|
|
9
|
+
contents: read
|
|
10
|
+
|
|
11
|
+
jobs:
|
|
12
|
+
publish:
|
|
13
|
+
runs-on: ubuntu-latest
|
|
14
|
+
environment: pypi
|
|
15
|
+
steps:
|
|
16
|
+
- uses: actions/checkout@v4
|
|
17
|
+
- uses: actions/setup-python@v5
|
|
18
|
+
with:
|
|
19
|
+
python-version: "3.12"
|
|
20
|
+
- run: pip install build
|
|
21
|
+
- run: python -m build
|
|
22
|
+
- uses: pypa/gh-action-pypi-publish@release/v1
|
|
@@ -0,0 +1,166 @@
|
|
|
1
|
+
# Byte-compiled / optimized / DLL files
|
|
2
|
+
__pycache__/
|
|
3
|
+
*.py[cod]
|
|
4
|
+
*$py.class
|
|
5
|
+
|
|
6
|
+
# C extensions
|
|
7
|
+
*.so
|
|
8
|
+
|
|
9
|
+
# IDE
|
|
10
|
+
.vscode
|
|
11
|
+
|
|
12
|
+
# Distribution / packaging
|
|
13
|
+
.Python
|
|
14
|
+
build/
|
|
15
|
+
develop-eggs/
|
|
16
|
+
dist/
|
|
17
|
+
downloads/
|
|
18
|
+
eggs/
|
|
19
|
+
.eggs/
|
|
20
|
+
lib/
|
|
21
|
+
lib64/
|
|
22
|
+
parts/
|
|
23
|
+
sdist/
|
|
24
|
+
var/
|
|
25
|
+
wheels/
|
|
26
|
+
share/python-wheels/
|
|
27
|
+
*.egg-info/
|
|
28
|
+
.installed.cfg
|
|
29
|
+
*.egg
|
|
30
|
+
MANIFEST
|
|
31
|
+
|
|
32
|
+
# PyInstaller
|
|
33
|
+
# Usually these files are written by a python script from a template
|
|
34
|
+
# before PyInstaller builds the exe, so as to inject date/other infos into it.
|
|
35
|
+
*.manifest
|
|
36
|
+
*.spec
|
|
37
|
+
|
|
38
|
+
# Installer logs
|
|
39
|
+
pip-log.txt
|
|
40
|
+
pip-delete-this-directory.txt
|
|
41
|
+
|
|
42
|
+
# Unit test / coverage reports
|
|
43
|
+
htmlcov/
|
|
44
|
+
.tox/
|
|
45
|
+
.nox/
|
|
46
|
+
.coverage
|
|
47
|
+
.coverage.*
|
|
48
|
+
.cache
|
|
49
|
+
nosetests.xml
|
|
50
|
+
coverage.xml
|
|
51
|
+
*.cover
|
|
52
|
+
*.py,cover
|
|
53
|
+
.hypothesis/
|
|
54
|
+
.pytest_cache/
|
|
55
|
+
cover/
|
|
56
|
+
|
|
57
|
+
# Translations
|
|
58
|
+
*.mo
|
|
59
|
+
*.pot
|
|
60
|
+
|
|
61
|
+
# Django stuff:
|
|
62
|
+
*.log
|
|
63
|
+
local_settings.py
|
|
64
|
+
db.sqlite3
|
|
65
|
+
db.sqlite3-journal
|
|
66
|
+
|
|
67
|
+
# Flask stuff:
|
|
68
|
+
instance/
|
|
69
|
+
.webassets-cache
|
|
70
|
+
|
|
71
|
+
# Scrapy stuff:
|
|
72
|
+
.scrapy
|
|
73
|
+
|
|
74
|
+
# Sphinx documentation
|
|
75
|
+
docs/_build/
|
|
76
|
+
|
|
77
|
+
# PyBuilder
|
|
78
|
+
.pybuilder/
|
|
79
|
+
target/
|
|
80
|
+
|
|
81
|
+
# Jupyter Notebook
|
|
82
|
+
.ipynb_checkpoints
|
|
83
|
+
|
|
84
|
+
# IPython
|
|
85
|
+
profile_default/
|
|
86
|
+
ipython_config.py
|
|
87
|
+
|
|
88
|
+
# pyenv
|
|
89
|
+
# For a library or package, you might want to ignore these files since the code is
|
|
90
|
+
# intended to run in multiple environments; otherwise, check them in:
|
|
91
|
+
# .python-version
|
|
92
|
+
|
|
93
|
+
# pipenv
|
|
94
|
+
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
|
|
95
|
+
# However, in case of collaboration, if having platform-specific dependencies or dependencies
|
|
96
|
+
# having no cross-platform support, pipenv may install dependencies that don't work, or not
|
|
97
|
+
# install all needed dependencies.
|
|
98
|
+
#Pipfile.lock
|
|
99
|
+
|
|
100
|
+
# poetry
|
|
101
|
+
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
|
|
102
|
+
# This is especially recommended for binary packages to ensure reproducibility, and is more
|
|
103
|
+
# commonly ignored for libraries.
|
|
104
|
+
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
|
|
105
|
+
#poetry.lock
|
|
106
|
+
|
|
107
|
+
# pdm
|
|
108
|
+
# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
|
|
109
|
+
#pdm.lock
|
|
110
|
+
# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
|
|
111
|
+
# in version control.
|
|
112
|
+
# https://pdm.fming.dev/latest/usage/project/#working-with-version-control
|
|
113
|
+
.pdm.toml
|
|
114
|
+
.pdm-python
|
|
115
|
+
.pdm-build/
|
|
116
|
+
|
|
117
|
+
# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
|
|
118
|
+
__pypackages__/
|
|
119
|
+
|
|
120
|
+
# Celery stuff
|
|
121
|
+
celerybeat-schedule
|
|
122
|
+
celerybeat.pid
|
|
123
|
+
|
|
124
|
+
# SageMath parsed files
|
|
125
|
+
*.sage.py
|
|
126
|
+
|
|
127
|
+
# Environments
|
|
128
|
+
.env
|
|
129
|
+
.cloudy_config
|
|
130
|
+
.venv
|
|
131
|
+
env/
|
|
132
|
+
venv/
|
|
133
|
+
ENV/
|
|
134
|
+
env.bak/
|
|
135
|
+
venv.bak/
|
|
136
|
+
|
|
137
|
+
# Spyder project settings
|
|
138
|
+
.spyderproject
|
|
139
|
+
.spyproject
|
|
140
|
+
|
|
141
|
+
# Rope project settings
|
|
142
|
+
.ropeproject
|
|
143
|
+
|
|
144
|
+
# mkdocs documentation
|
|
145
|
+
/site
|
|
146
|
+
|
|
147
|
+
# mypy
|
|
148
|
+
.mypy_cache/
|
|
149
|
+
.dmypy.json
|
|
150
|
+
dmypy.json
|
|
151
|
+
|
|
152
|
+
# Pyre type checker
|
|
153
|
+
.pyre/
|
|
154
|
+
|
|
155
|
+
# pytype static type analyzer
|
|
156
|
+
.pytype/
|
|
157
|
+
|
|
158
|
+
# Cython debug symbols
|
|
159
|
+
cython_debug/
|
|
160
|
+
|
|
161
|
+
# PyCharm
|
|
162
|
+
# JetBrains specific template is maintained in a separate JetBrains.gitignore that can
|
|
163
|
+
# be found at https://github.com/github/gitignore/blob/main/Global/JetBrains.gitignore
|
|
164
|
+
# and can be added to the global gitignore or merged into this file. For a more nuclear
|
|
165
|
+
# option (not recommended) you can uncomment the following to ignore the entire idea folder.
|
|
166
|
+
#.idea/
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project are documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.1.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
## [Unreleased]
|
|
9
|
+
|
|
10
|
+
## [0.2.0] - 2026-08-14
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
|
|
14
|
+
- Hero README, CI badges, contributing guide, issue templates
|
|
15
|
+
- Fixture-backed example generated sObjects under `examples/generated/`
|
|
16
|
+
- mypy in CI; CLI logging for `cloudy-salesforce generate`
|
|
17
|
+
- `SalesforceClient.from_config()` to build a client from `.cloudy_config` and env vars
|
|
18
|
+
- `cloudy-salesforce init` to scaffold `.cloudy_config` and `.env.example`
|
|
19
|
+
- Typed `insert` / `update` / `upsert` / `delete` from `@sobject` dataclasses
|
|
20
|
+
- `DmlResult` return type for composite DML
|
|
21
|
+
- `SalesforceError` with `error_code` and `status_code` for REST failures
|
|
22
|
+
- JWT bearer and session-token authentication (`JwtBearerAuthentication`, `SessionAuthentication`) with `.cloudy_config` aliases
|
|
23
|
+
- Optional rate-limit retries on HTTP 429 and `REQUEST_LIMIT_EXCEEDED` in `SalesforceClient.request`
|
|
24
|
+
- GitHub Actions Trusted Publisher workflow to publish to PyPI on GitHub release
|
|
25
|
+
|
|
26
|
+
### Changed
|
|
27
|
+
|
|
28
|
+
- `SalesforceClient` no longer becomes the default instance on construction; use `default=True` or `set_default_instance()`
|
|
29
|
+
- Ignore local `.cloudy_config` so `init` output is not committed by accident
|
|
30
|
+
- Generated `date` / `datetime` fields are `datetime.date` / `datetime.datetime` instead of `str` (regenerate sObjects to pick this up)
|
|
31
|
+
|
|
32
|
+
## [0.1.0] - 2026-08-14
|
|
33
|
+
|
|
34
|
+
### Added
|
|
35
|
+
|
|
36
|
+
- Typed Salesforce client: username/password SOAP auth, SOQL with pagination and `parse_as`, composite CRUD, describe-driven dataclass codegen
|
|
37
|
+
|
|
38
|
+
[Unreleased]: https://github.com/fishygeek91/cloudy-salesforce/compare/v0.2.0...HEAD
|
|
39
|
+
[0.2.0]: https://github.com/fishygeek91/cloudy-salesforce/compare/v0.1.0...v0.2.0
|
|
40
|
+
[0.1.0]: https://github.com/fishygeek91/cloudy-salesforce/releases/tag/v0.1.0
|
|
@@ -0,0 +1,38 @@
|
|
|
1
|
+
# Contributing
|
|
2
|
+
|
|
3
|
+
Thanks for helping improve [cloudy-salesforce](https://github.com/fishygeek91/cloudy-salesforce).
|
|
4
|
+
|
|
5
|
+
## Development setup
|
|
6
|
+
|
|
7
|
+
- **Python 3.10+** is required.
|
|
8
|
+
- Install the package and dev dependencies:
|
|
9
|
+
|
|
10
|
+
```bash
|
|
11
|
+
pip install -e ".[dev]"
|
|
12
|
+
```
|
|
13
|
+
|
|
14
|
+
## Running checks
|
|
15
|
+
|
|
16
|
+
Run these before opening a pull request:
|
|
17
|
+
|
|
18
|
+
```bash
|
|
19
|
+
pytest
|
|
20
|
+
ruff check cloudy_salesforce tests
|
|
21
|
+
mypy cloudy_salesforce
|
|
22
|
+
```
|
|
23
|
+
|
|
24
|
+
Tests use mocks and fixtures. CI and the default test suite do **not** connect to a live Salesforce org.
|
|
25
|
+
|
|
26
|
+
## Secrets and local config
|
|
27
|
+
|
|
28
|
+
Do not commit `.env`, `.cloudy_config`, or any credentials. Use environment variables or local config files that stay out of version control.
|
|
29
|
+
|
|
30
|
+
## Pull requests
|
|
31
|
+
|
|
32
|
+
- Branch from `main` and open PRs against `main`.
|
|
33
|
+
- Keep changes focused and include tests when behavior changes.
|
|
34
|
+
|
|
35
|
+
## Code style
|
|
36
|
+
|
|
37
|
+
- Match patterns in existing modules (typing, naming, structure).
|
|
38
|
+
- Keep tests mocked; avoid requiring a real org unless explicitly documented as an integration test.
|
|
@@ -0,0 +1,21 @@
|
|
|
1
|
+
MIT License
|
|
2
|
+
|
|
3
|
+
Copyright (c) 2024 fishygeek91
|
|
4
|
+
|
|
5
|
+
Permission is hereby granted, free of charge, to any person obtaining a copy
|
|
6
|
+
of this software and associated documentation files (the "Software"), to deal
|
|
7
|
+
in the Software without restriction, including without limitation the rights
|
|
8
|
+
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
|
|
9
|
+
copies of the Software, and to permit persons to whom the Software is
|
|
10
|
+
furnished to do so, subject to the following conditions:
|
|
11
|
+
|
|
12
|
+
The above copyright notice and this permission notice shall be included in all
|
|
13
|
+
copies or substantial portions of the Software.
|
|
14
|
+
|
|
15
|
+
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
|
16
|
+
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
|
17
|
+
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
|
|
18
|
+
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
|
|
19
|
+
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
|
|
20
|
+
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
|
21
|
+
SOFTWARE.
|