Repository navigation
Fix/application number slash - #319
Conversation
There was a problem hiding this comment.
An organization admin can view or raise the monthly spending cap at claude.ai/admin-settings/usage, on the Claude Code Review row under Services. The cap resets at the start of the next billing period.
Once the cap resets or is raised, someone with write access to this repository can comment @claude review on this pull request to trigger a review.
| application_number( | ||
| "patentApplicationNumber", patent_application_number_q | ||
| ), | ||
| contains("legalSectionCode", legal_section_code_q), |
There was a problem hiding this comment.
🟣 pre-existing, not blocking: pre-existing: Callers who follow the new docstring and pass legal_section_code_q="101 OR 103" get a broken criteria string instead of an OR filter. contains without quoted sends the value raw as legalSectionCode:*101 OR 103*, so the field applies only to *101 and the rest is searched as free text. Fix: wrap any value that contains whitespace in parentheses, in both unquoted contains and the pass-through branches of publication_number, which covers the 3 sites listed. Same pattern at 3 sites (oa_citations.py:159, query.py:185, query.py:188).
A small fix can ride a push you are already making; otherwise a short reply is enough.
Why this was flagged
The new docstring at oa_citations.py:90-93 says every convenience filter is a code filter and that a value containing spaces is wrapped in parentheses. legal_section_code_q goes through contains("legalSectionCode", ...) at oa_citations.py:159. With quoted=False that path returns f"{field}:*{value}*" (query.py:230) and never checks for whitespace. publication_number behaves the same way: a value with *, or one that _PUBLICATION_NUMBER_RE does not match (for example "20210138233 OR 20210138234"), is returned as f"{field}:{text}" at query.py:185/188 with no parentheses. In both cases only the first term is tied to the field, so search_citations/search_applications return wrong or unrelated records. The base branch built the same strings, so this is pre-existing. The PR does say code filters with expressions now get parentheses in every search client, and these two builders do not.
Verification: Pre-existing. The new docstring at oa_citations.py:90-93 says a value that contains spaces "is wrapped in parentheses, so the field applies to every term." But oa_citations.py:159 calls contains("legalSectionCode", legal_section_code_q), whose unquoted branch is return f"{field}:*{value}*", with no whitespace check. So the criteria becomes legalSectionCode:*101 OR 103*. The base built exactly the same string.
Description
Fixes application-number handling across the library, and moves every client's search-filter query building into one shared module.
sanitize_application_numbernow returns series-code input as 8 digits (18/511,739→18511739). It used to keep the slash, soget_application_by_numberand the other per-applicationPatentDataClientmethods requested a path the API rejects with HTTP 403.application_number_q,application_number_text_q,patent_application_number_q, and the PTAB interference party filters) now go through the same cleanup. Before,17/765301matched nothing in any of them.pyUSPTO.clients.query, holds the functions that build each query clause (term,phrase,contains,any_of,date_range,application_number,either,all_of, and others). Every search method now builds itsqorcriteriavalue with them. That fixes the inconsistent quoting:document_type_description_q.office_action_category_q="CTNF OR CTFR"works.customer_number_q=[]) raisesValueErrorinstead of running the search unfiltered.PetitionDecisionsClient.get_decision_by_id,BulkDataClient.get_product_by_id, and theBulkDataClient.download_filefallback percent-encode IDs and file names in the URL path. Non-string IDs such asuuid.UUIDstill work.BulkDataClient.download_file(file_name=...)usesfile_nameonly as the local save name. It used to request that name from the server.Missing Authentication Tokennow says the requested path may not exist.examples/error_handling_example.pysays so too.Type of Change
Testing
Checklist
Related Issues
N/A
Additional Notes
appellant_name_q="Block, Inc."returned 4303 PTAB appeal decisions from 2025 instead of 1, becauseInc.was searched as free text.patent_number_q="10000000 OR 10000001"returned 3 applications instead of 2.inventor_name_q='Smith "John'returned nothing.NN/NNNNNNapplication numbers matched nothing in any search client.office_action_category_q="CTNF OR CTFR"for application 15061308 returned 0 citations instead of 25.trialStatusCategory:InstitutedandtrialStatusCategory:"Instituted"both return 220 proceedings.Garcia-Lopez*) is quoted, so the wildcard is searched as plain text. Live,"Garcia-Lopez*"returns the same 119 applications as"Garcia-Lopez". Both the unquoted and backslash-escaped forms return HTTP 404, so there is no form that makes the wildcard expand. The docstring and CHANGELOG say so.sanitize_application_numberreturns a different string for series-code input, but the old form never worked in a lookup. An empty list filter now raises, but it used to send a malformedfield:()clause.BulkDataClientchanges are covered by unit tests.test_ptab_appeals_integration.pyno longer wraps API calls intry/except. The same pattern is still in the patent data, petition, PTAB interferences, and PTAB trials live test files, which is follow-up work.