READ-ONLY PACKAGE PREVIEW

wp-rest-api/examples/probe-rest-fixture.py

Version 34da134e184e.bb2 · GPL-2.0-or-later. This preview displays packaged text and does not execute code. Treat the contents as untrusted instructions.

← Return to resource and package checksum

"""BB Skills synthetic HTTP probe; GPL-2.0-or-later. Ephemeral keys arrive on stdin and are never printed."""
import base64,datetime as dt,json,sys,urllib.request,urllib.error
base='http://bb-v42-rest-wp';keys=json.load(sys.stdin);cases=[]
def request(route,method='GET',body=None,mode=None):
 headers={'User-Agent':'BB-Skills-native-REST-fixture/1.0','Accept':'application/json'}
 if mode in ['editor','subscriber']:headers['Authorization']='Basic '+base64.b64encode((keys[mode]['username']+':'+keys[mode]['password']).encode()).decode()
 if mode in ['cookie','cookie_nonce','cookie_bad_nonce']:
  headers['Cookie']=keys['cookie']
  if mode=='cookie_nonce':headers['X-WP-Nonce']=keys['nonce']
  elif mode=='cookie_bad_nonce':headers['X-WP-Nonce']='invalid-fixture-nonce'
 data=json.dumps(body).encode() if body is not None else None
 if data is not None:headers['Content-Type']='application/json'
 req=urllib.request.Request(base+'/?rest_route='+route,data=data,headers=headers,method=method)
 try:
  with urllib.request.urlopen(req,timeout=15) as r:status=r.status;raw=r.read();h={k.lower():v for k,v in r.headers.items()}
 except urllib.error.HTTPError as r:status=r.code;raw=r.read();h={k.lower():v for k,v in r.headers.items()}
 return status,json.loads(raw),h

def record(name,actual,status,check=lambda body,headers:True,classification='native synthetic HTTP observation'):
 code,body,headers=actual
 if code!=status or not check(body,headers):raise AssertionError(json.dumps({'case':name,'status':code,'body':body,'headers':{k:v for k,v in headers.items() if k.startswith('x-wp-')}}))
 cases.append({'name':name,'status':'passed','http_status':code,'classification':classification,'response':body,'pagination_headers':{k:v for k,v in headers.items() if k in ['x-wp-total','x-wp-totalpages']}})

if keys.get('phase')=='revoked':
 for role in ['editor','subscriber']:record(role+'_application_password_revoked',request('/wp/v2/users/me',mode=role),401,lambda b,h:b.get('code')=='rest_not_logged_in')
else:
 record('api_namespace_discovery',request('/'),200,lambda b,h:'bb-fixture/v1' in b['namespaces'])
 record('options_schema_discovery',request('/bb-fixture/v1/restricted',method='OPTIONS'),200,lambda b,h:any(e['args']['count'].get('minimum')==1 and e['args']['count'].get('maximum')==5 and e['args']['count']['required'] for e in b['endpoints']))
 record('anonymous_restricted_denied',request('/bb-fixture/v1/restricted','POST',{'count':2}),401,lambda b,h:b['code']=='rest_forbidden')
 record('authenticated_subscriber_denied',request('/bb-fixture/v1/restricted','POST',{'count':2},'subscriber'),403,lambda b,h:b['code']=='rest_forbidden')
 record('subscriber_is_authenticated',request('/wp/v2/users/me',mode='subscriber'),200,lambda b,h:b['id']==keys['subscriber']['id'])
 record('negative_control_login_only_leaks_marker',request('/bb-fixture/v1/weak-auth-only',mode='subscriber'),200,lambda b,h:b=={'synthetic_private_marker':'FIXTURE_ONLY'},'intentional fixture authorization defect; not an upstream skill vulnerability')
 for name,payload in [('required_count_missing',{}),('count_below_minimum',{'count':0}),('count_above_maximum',{'count':6}),('count_non_numeric',{'count':'wrong'}),('note_wrong_type',{'count':2,'note':[]} )]:
  record(name,request('/bb-fixture/v1/restricted','POST',payload,'editor'),400,lambda b,h:b['code'] in ['rest_missing_callback_param','rest_invalid_param'])
 record('denied_and_invalid_requests_do_not_call_callback',request('/bb-fixture/v1/status'),200,lambda b,h:b['callback_count']==0)
 record('editor_authorized_and_text_sanitized',request('/bb-fixture/v1/restricted','POST',{'count':2,'note':'<b>example</b>\n spaced'},'editor'),200,lambda b,h:b=={'count':2,'note':'example spaced','calls':1})
 record('cookie_without_nonce_is_anonymous',request('/bb-fixture/v1/restricted','POST',{'count':2},'cookie'),401,lambda b,h:b['code']=='rest_forbidden')
 record('cookie_invalid_nonce_denied',request('/bb-fixture/v1/restricted','POST',{'count':2},'cookie_bad_nonce'),403,lambda b,h:b['code']=='rest_cookie_invalid_nonce')
 record('cookie_with_valid_nonce_authorized',request('/bb-fixture/v1/restricted','POST',{'count':3,'note':'cookie fixture'},'cookie_nonce'),200,lambda b,h:b=={'count':3,'note':'cookie fixture','calls':2})
 record('cpt_route_fields_and_object_meta',request('/wp/v2/bb_notes&per_page=1'),200,lambda b,h:len(b)==1 and all(k in b[0] for k in ['id','title','content','bb_fixture_summary','meta']) and b[0]['meta']['bb_fixture_flags']=={'approved':True})
 record('fields_limits_response_without_removing_core_schema',request('/wp/v2/bb_notes&per_page=1&_fields=id,bb_fixture_summary'),200,lambda b,h:len(b)==1 and set(b[0])=={'id','bb_fixture_summary'})
 records=[]
 for n,ids in [(1,[1,2]),(2,[3,4]),(3,[5])]:
  result=request('/bb-fixture/v1/items&page='+str(n)+'&per_page=2');record('pagination_page_'+str(n),result,200,lambda b,h,ids=ids:[v['id'] for v in b]==ids and h['x-wp-total']=='5' and h['x-wp-totalpages']=='3');records.extend(v['id'] for v in result[1])
 assert records==[1,2,3,4,5]
 record('pagination_out_of_range',request('/bb-fixture/v1/items&page=4&per_page=2'),400,lambda b,h:b['code']=='bb_page_unavailable')
 record('per_page_above_100_rejected',request('/bb-fixture/v1/items&per_page=101'),400,lambda b,h:b['code']=='rest_invalid_param')
 record('missing_route_is_404',request('/bb-fixture/v1/no-such-route'),404,lambda b,h:b['code']=='rest_no_route')
 record('only_two_authorized_calls_reached_callback',request('/bb-fixture/v1/status'),200,lambda b,h:b['callback_count']==2)
print(json.dumps({'executed_at':dt.datetime.now(dt.UTC).isoformat(),'cases':cases,'observations':len(cases),'environment':keys['environment'],'probe_python':sys.version.split()[0],'scope':'Hand-authored synthetic WordPress HTTP fixture. No AI client, upstream benchmark harness, production WordPress instance or external credentials. Internal HTTP only; HTTPS transport and real browser login were not tested.','runtime_tested':False,'native_fixture_tested':True}))