Skip to content

Commit

Permalink
Implements Ability to Annotate Offers on CSFloat
Browse files Browse the repository at this point in the history
  • Loading branch information
Step7750 committed Apr 3, 2024
1 parent 262a725 commit 5ff4355
Show file tree
Hide file tree
Showing 5 changed files with 115 additions and 0 deletions.
30 changes: 30 additions & 0 deletions src/lib/bridge/handlers/annotate_offer.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import {SimpleHandler} from './main';
import {RequestType} from './types';

export interface AnnotateOfferRequest {
assets_to_send: string[];
assets_to_receive: string[];
offer_id: string;
}

export interface AnnotateOfferResponse {}

export const AnnotateOffer = new SimpleHandler<AnnotateOfferRequest, AnnotateOfferResponse>(
RequestType.ANNOTATE_OFFER,
async (req) => {
const resp = await fetch(`https://csfloat.com/api/v1/trades/annotate-offer`, {
credentials: 'include',
method: 'POST',
headers: {
'Content-Type': 'application/json',
},
body: JSON.stringify(req),
});

if (resp.status !== 200) {
throw new Error('invalid status');
}

return resp.json() as Promise<AnnotateOfferResponse>;
}
);
2 changes: 2 additions & 0 deletions src/lib/bridge/handlers/handlers.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import {FetchSkinModel} from './fetch_skin_model';
import {StorageRemove} from './storage_remove';
import {RequestType} from './types';
import {FetchExtensionFile} from './fetch_extension_file';
import {AnnotateOffer} from './annotate_offer';

export const HANDLERS_MAP: {[key in RequestType]: RequestHandler<any, any>} = {
[RequestType.EXECUTE_SCRIPT_ON_PAGE]: ExecuteScriptOnPage,
Expand All @@ -22,4 +23,5 @@ export const HANDLERS_MAP: {[key in RequestType]: RequestHandler<any, any>} = {
[RequestType.FETCH_PENDING_TRADES]: FetchPendingTrades,
[RequestType.FETCH_SKIN_MODEL]: FetchSkinModel,
[RequestType.FETCH_EXTENSION_FILE]: FetchExtensionFile,
[RequestType.ANNOTATE_OFFER]: AnnotateOffer,
};
1 change: 1 addition & 0 deletions src/lib/bridge/handlers/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -9,4 +9,5 @@ export enum RequestType {
FETCH_PENDING_TRADES,
FETCH_SKIN_MODEL,
FETCH_EXTENSION_FILE,
ANNOTATE_OFFER,
}
62 changes: 62 additions & 0 deletions src/lib/page_scripts/trade_offer.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,16 @@ import '../components/trade_offer/trade_item_holder_metadata';
import '../components/trade_offer/auto_fill';
import {ClassIdAndInstanceId, rgDescription, rgInventoryAsset, TradeInventory} from '../types/steam';
import {fetchRegisteredSteamAPIKey} from '../utils/key';
import {deserializeForm} from '../utils/browser';
import {AppId} from '../types/steam_constants';
import {ClientSend} from '../bridge/client';
import {AnnotateOffer} from '../bridge/handlers/annotate_offer';
import {of} from 'rxjs';

init('src/lib/page_scripts/trade_offer.js', main);

async function main() {
injectAnnotateOffer();
injectInventoryFallback();
}

Expand Down Expand Up @@ -117,3 +123,59 @@ function injectInventoryFallback() {
);
};
}

interface JsonTradeofferAsset {
appid: number;
contextid: string;
amount: number;
assetid: string;
}

interface JsonTradeoffer {
me: {
assets: JsonTradeofferAsset[];
};
them: {
assets: JsonTradeofferAsset[];
};
version: number;
}

function injectAnnotateOffer() {
// Annotate offers for use in CSFloat Market, if the user isn't logged into CSFloat this does nothing
// Similarly if they don't have an active sale, it does nothing
$J(document).on('ajaxComplete', async (event, request, settings) => {
if (!settings.url.includes('tradeoffer/new/send')) {
// Ignore requests that aren't a new trade offer
return;
}

const offer_id = request?.responseJSON?.tradeofferid;

if (!offer_id) {
// Something wrong with the format
return;
}

let assets_to_send: string[] = [];
let assets_to_receive: string[] = [];
const deserialized = deserializeForm(settings.data) as {json_tradeoffer?: string};

if (deserialized && deserialized.json_tradeoffer) {
try {
const parsed = JSON.parse(deserialized.json_tradeoffer) as JsonTradeoffer;
assets_to_send = parsed.me.assets.filter((e) => e.appid === AppId.CSGO).map((e) => e.assetid);
assets_to_receive = parsed.them.assets.filter((e) => e.appid === AppId.CSGO).map((e) => e.assetid);
} catch (e) {
console.error('failed to parse json tradeoffer', e, deserialized.json_tradeoffer);
// Still proceed with annotating the offer id on a best-effort
}
}

await ClientSend(AnnotateOffer, {
assets_to_send,
assets_to_receive,
offer_id: offer_id,
});
});
}
20 changes: 20 additions & 0 deletions src/lib/utils/browser.ts
Original file line number Diff line number Diff line change
Expand Up @@ -10,3 +10,23 @@ export function getQueryParameter(param: string): string | null {
export function hasQueryParameter(param: string): boolean {
return !!getQueryParameter(param);
}

export function deserializeForm(serialized: string): any {
if (serialized.slice(0, 1) === '?') {
serialized = serialized.slice(1);
}

if (!serialized) {
return {};
}

return serialized.split('&').reduce((acc: any, e) => {
const pair = e.split('=');
if (pair.length < 2) {
return acc;
}

acc[decodeURIComponent(pair[0])] = decodeURIComponent(pair[1]);
return acc;
}, {});
}

0 comments on commit 5ff4355

Please sign in to comment.