Skip to content

Commit

Permalink
Add files via upload
Browse files Browse the repository at this point in the history
  • Loading branch information
Tapanhaz authored Jul 9, 2023
1 parent e39958b commit 02fe943
Show file tree
Hide file tree
Showing 10 changed files with 357 additions and 0 deletions.
3 changes: 3 additions & 0 deletions build/lib/mcxpy/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
from .mcx import mcx_bhavcopy, mcx_marketwatch, mcx_circulars, mcx_topgainers, mcx_toploosers, mcx_mostactiveoptions, mcx_mostactivecontracts, mcx_heatmap, mcx_optionchain, mcx_pcr, mcx_expiry

__all__ = ['mcx_bhavcopy', 'mcx_marketwatch', 'mcx_circulars', 'mcx_topgainers', 'mcx_toploosers', 'mcx_mostactiveoptions', 'mcx_mostactivecontracts', 'mcx_heatmap', 'mcx_optionchain', 'mcx_pcr', 'mcx_expiry']
1 change: 1 addition & 0 deletions build/lib/mcxpy/__init__.pyi
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
from .mcx import mcx_bhavcopy as mcx_bhavcopy, mcx_circulars as mcx_circulars, mcx_expiry as mcx_expiry, mcx_heatmap as mcx_heatmap, mcx_marketwatch as mcx_marketwatch, mcx_mostactivecontracts as mcx_mostactivecontracts, mcx_mostactiveoptions as mcx_mostactiveoptions, mcx_optionchain as mcx_optionchain, mcx_pcr as mcx_pcr, mcx_topgainers as mcx_topgainers, mcx_toploosers as mcx_toploosers
326 changes: 326 additions & 0 deletions build/lib/mcxpy/mcx.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,326 @@
import requests
import pandas as pd
from datetime import datetime, date, timedelta
import re
from typing import Literal, Union, NewType, List, Tuple

DateFormat = NewType(name="%d-%m-%Y", tp=str)
DateFormat_2 = NewType(name="%Y%m%d", tp=str)
DateFormat_3 = NewType(name="%d%b%Y", tp=str)

urls = {
"base_url" : "https://www.mcxindia.com",
"routes" : {
"bhavcopy" : "/backpage.aspx/GetDateWiseBhavCopy",
"marketwatch" : "/backpage.aspx/GetMarketWatch",
"circulars" : "/backpage.aspx/GetCircularAdvanceSearch",
"gainers" : "/backpage.aspx/GetGainer",
"losers" : "/backpage.aspx/GetLosers",
"activeoptions" : "/backpage.aspx/GetMostActiveOptionsContractsByValue",
"activecontracts" : "/backpage.aspx/GetMostActiveContractByValueFilter",
"heatmap" : "/backpage.aspx/GetHeatMap",
"optionchain" : "/backpage.aspx/GetOptionChain",
"pcr" : "/backpage.aspx/GetCommoditywisePutCallRatio",
"pcr_expirywise" : "/backpage.aspx/GetExpirywisePutCallRatio"
},
}


headers = {
"Accept": "application/json, text/javascript, */*; q=0.01",
"Accept-Language": "en-GB,en-US;q=0.9,en;q=0.8",
"Cache-Control": "no-cache",
"Connection": "keep-alive",
"Content-Type": "application/json",
"Origin": "https://www.mcxindia.com",
"Referer": "https://www.mcxindia.com",
"Pragma": "no-cache",
"Sec-Fetch-Dest": "empty",
"Sec-Fetch-Mode": "cors",
"Sec-Fetch-Site": "same-origin",
"User-Agent": "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/114.0.0.0 Safari/537.36",
"X-Requested-With": "XMLHttpRequest",
"sec-ch-ua": "^\"Not.A/Brand^\";v=^\"8^\", ^\"Chromium^\";v=^\"114^\", ^\"Google Chrome^\";v=^\"114^\"",
"sec-ch-ua-mobile": "?0",
"sec-ch-ua-platform": "^\"Windows^\"",
}



def format_date(dateobj: Union[DateFormat, datetime, date],
isExpiry=False
) -> Union[DateFormat_2, DateFormat_3]:

if isinstance(dateobj, str):
try:
if isExpiry:
dt = datetime.strptime(dateobj, "%d-%m-%Y")
return dt.strftime("%d%b%Y").upper()
dt = datetime.strptime(dateobj, "%d-%m-%Y")
return dt.strftime("%Y%m%d")
except ValueError as e:
print(f"Format Date String Error :: {e}")
return
elif isinstance(dateobj, datetime) or isinstance(dateobj, date):
if isExpiry:
return dateobj.strftime("%d%b%Y").upper()
return dateobj.strftime("%Y%m%d")
else:
print("Invalid input type. Expected str(dd-mm-yyyy), date or datetime.")

def convert_to_ist(timestamp_str: str) -> datetime:
try:
match_str = re.search(r'\((-?\d+)\)', timestamp_str)
if match_str:
timestamp_ms = int(match_str.group(1))

if timestamp_ms <= 0:
return None

ist_datetime = datetime.utcfromtimestamp(timestamp_ms / 1000) + timedelta(hours=5, minutes=30)
return ist_datetime
return None
except Exception as e:
print(f"Error :: {e}")

def mcxfetch(config_key: Literal["bhavcopy","marketwatch","circulars","gainers","losers","activeoptions",
"activecontracts","heatmap","optionchain","pcr", "pcr_expirywise"],
data: dict=None) -> dict:
try:
base_url = urls['base_url']
url = base_url + urls['routes'][config_key]
response = requests.post(url, headers=headers, json=data)
response.raise_for_status()
if response.status_code == 200:
res_data = response.json()
return res_data
except (requests.HTTPError,Exception) as e:
print(f"Error :: {e}")

def mcx_bhavcopy(bhavdate: Union[DateFormat, datetime, date]) -> pd.DataFrame:
try:
fdate = format_date(bhavdate)

data = {
"Date": fdate,
"InstrumentName": "ALL"
}

res = mcxfetch(config_key='bhavcopy',data=data)
df = pd.DataFrame(res["d"]["Data"])
selected_columns = [
'DateDisplay', 'InstrumentName', 'Symbol', 'ExpiryDate', 'OptionType', 'StrikePrice',
'Open', 'High', 'Low', 'Close', 'PreviousClose', 'Volume', 'VolumeInThousands',
'Value', 'OpenInterest'
]
df = df[selected_columns]
df = df.rename(columns={
'DateDisplay' : 'Date',
'InstrumentName' : 'Instrument Name',
'ExpiryDate' : 'Expiry Date',
'OptionType' : 'Option Type',
'StrikePrice' : 'Strike Price',
'PreviousClose' : 'Previous Close',
'Volume' : 'Volume(Lots)',
'Value' : 'Value(Lacs)',
'OpenInterest' : 'Open Interest(Lots)'
})
df['Date'] = pd.to_datetime(df['Date'], format='mixed',dayfirst=True)
df['Expiry Date'] = pd.to_datetime(df['Expiry Date'], format='mixed',dayfirst=True)
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_marketwatch() -> pd.DataFrame:
try:
res = mcxfetch(config_key='marketwatch')
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['__type'])
df = df.replace('-', '')
df = df.rename(columns={
'ProductCode': 'Product',
'ExpiryDate': 'Expiry',
'BuyQuantity': 'BuyQty',
'SellQuantity': 'SellQty'
})
df['Expiry'] = pd.to_datetime(df['Expiry'], format='mixed',dayfirst=True)
df['UnderlineContract'] = pd.to_datetime(df['UnderlineContract'], format='mixed', dayfirst=True)
df['LTT'] = df['LTT'].apply(convert_to_ist)
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_circulars(from_date: Union[DateFormat, datetime, date] =(datetime.now()-timedelta(days=4)),
to_date: Union[DateFormat, datetime, date]=datetime.now()
) -> pd.DataFrame:
try:
date1 = format_date(from_date)
date2 = format_date(to_date)

data = {
'CircularType':'ALL',
'CircularNo':'',
'Title':'',
'FromDate': date1,
'ToDate': date2
}

res = mcxfetch(config_key='circulars', data=data)
df= pd.DataFrame(res['d'])
df = df.drop(columns=['__type', 'CircularDate','CircularMonth','CircularYear','CircularTypes', 'CircularNumber'])
df['DisplayCircularDate'] = pd.to_datetime(df['DisplayCircularDate'], format='mixed', dayfirst=True)
df['CompareDate'] = pd.to_datetime(df['CompareDate'], format="%Y%m%d", yearfirst=True)
df = df.rename(columns={
'DisplayCircularDate': 'Date'
})
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_topgainers() -> pd.DataFrame:
try:
res = mcxfetch(config_key='gainers')
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['ExtensionData', 'EngSymbol'])
df['LTT'] = df['LTT'].apply(convert_to_ist)
df['ExpiryDate'] = pd.to_datetime(df['ExpiryDate'], format='%d%b%Y', dayfirst=True)
reorderd_columns = ['Symbol', 'LTT', 'ExpiryDate','PreviousClosed', 'LTP',
'AbsoluteChange', 'PercentChange']
df = df[reorderd_columns]
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_toploosers() -> pd.DataFrame:
try:
res = mcxfetch(config_key='losers')
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['ExtensionData', 'EngSymbol'])
df['LTT'] = df['LTT'].apply(convert_to_ist)
df['ExpiryDate'] = pd.to_datetime(df['ExpiryDate'], format='%d%b%Y', dayfirst=True)
reorderd_columns = ['Symbol', 'LTT', 'ExpiryDate','PreviousClosed', 'LTP',
'AbsoluteChange', 'PercentChange']
df = df[reorderd_columns]
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_mostactiveoptions() -> pd.DataFrame:
try:
option_list = ['CE', 'PE']
inst_list = ['OPTFUT', 'OPTCOM']

res_list = []
for opt in option_list:
for inst in inst_list:
data = {
'OptionType':opt,
'Product':'ALL',
'InstrumentType':inst
}
res = mcxfetch(config_key="activeoptions", data=data)
res_data = res["d"]["Data"]
res_list.append(res_data)
dfs = [pd.DataFrame(sublist) for sublist in res_list]
df = pd.concat(dfs)
df = df.drop(columns=['ExtensionData', 'EngSymbol'])
df['LTT'] = df['LTT'].apply(convert_to_ist)
df['ExpiryDate'] = pd.to_datetime(df['ExpiryDate'], format='mixed', dayfirst=True)
reorderd_columns = ['Symbol', 'LTT', 'ExpiryDate', 'InstrumentType', 'OptionType', 'StrikePrice', 'LTP','OpenInterest',
'Volume', 'PremiumValueInLacs','NotionalValueInLacs', 'ValueOfUnderlying']
df = df[reorderd_columns]
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_mostactivecontracts() -> pd.DataFrame:
try:
data = {
"InstrumentType": "ALL"
}
res = mcxfetch(config_key='activecontracts', data=data)
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['ExtensionData', 'EngSymbol'])
df['Date'] = df['Date'].apply(convert_to_ist)
df['ExpiryDate'] = pd.to_datetime(df['ExpiryDate'], format='mixed', dayfirst=True)
reorderd_columns = ['Symbol', 'Date', 'ExpiryDate', 'InstrumentName', 'OptionType', 'StrikePrice', 'LTP',
'PercentageChange','OpenInterest', 'Volume', 'Value','NotionalValue', 'PremiumValue',
'UnderlineValue', 'Unit']
df = df[reorderd_columns]
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_heatmap() -> pd.DataFrame:
try:
res = mcxfetch(config_key='heatmap')
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['__type'])
df['Dttm'] = df['Dttm'].apply(convert_to_ist)
df['ExpiryDate'] = pd.to_datetime(df['ExpiryDate'], format='mixed', dayfirst=True)
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_optionchain(commodity: Literal['COPPER', 'CRUDEOIL', 'GOLD', 'GOLDM', 'NATURALGAS',
'NICKEL', 'SILVER', 'SILVERM','ZINC'],
expiry: Union[DateFormat, datetime, date]
) -> pd.DataFrame:
try:
exp_date = format_date(dateobj=expiry, isExpiry=True)
data = {
'Commodity': commodity,
'Expiry': exp_date
}
res = mcxfetch(config_key='optionchain', data=data)
df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['ExtensionData'])
df['LTT'] = df['LTT'].apply(convert_to_ist)
df['CE_LTT'] = df['CE_LTT'].apply(convert_to_ist)
df['PE_LTT'] = df['PE_LTT'].apply(convert_to_ist)
df['Symbol'] = commodity
df['Expiry'] = datetime.strptime(exp_date, "%d%b%Y")
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_pcr(expirywise: bool=False) -> pd.DataFrame:
try:
if expirywise:
res = mcxfetch(config_key='pcr_expirywise')
else:
res = mcxfetch(config_key='pcr')

df = pd.DataFrame(res["d"]["Data"])
df = df.drop(columns=['ExtensionData'])
df['Date'] = df['Date'].apply(convert_to_ist)
if expirywise:
df['Expiry'] = pd.to_datetime(df['Expiry'], format="%d%b%Y", dayfirst=True, errors="coerce")
reorderd_columns = ['Symbol', 'Date', 'Expiry', 'Ratio']
df = df[reorderd_columns]
return df
except Exception as e:
print(f"Error :: {e}")

def mcx_expiry(commodity: Literal['COPPER', 'CRUDEOIL', 'GOLD', 'GOLDM', 'NATURALGAS',
'NICKEL', 'SILVER', 'SILVERM','ZINC']='CRUDEOIL',
expirytype : Literal['current', 'next', 'far', 'all']='current'
) -> Union[datetime,List[datetime]]:
try:
exp_df = mcx_pcr(expirywise=True)
com_df = exp_df[exp_df['Symbol'] == commodity]
exp_list = sorted(com_df['Expiry'].unique().tolist())
exp_list = [item.to_pydatetime() for item in exp_list]
if expirytype == "current":
return exp_list[0]
elif expirytype == "next":
return exp_list[1]
elif expirytype == "far":
return exp_list[2]
elif expirytype == "all":
return exp_list
else:
print("Please input correct parameters.")
except Exception as e:
print(f"Error :: {e}")

Empty file added build/lib/mcxpy/py.typed
Empty file.
Binary file added dist/mcxpy-0.0.1-py3-none-any.whl
Binary file not shown.
5 changes: 5 additions & 0 deletions mcxpy.egg-info/PKG-INFO
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
Metadata-Version: 2.1
Name: mcxpy
Version: 0.0.1
Summary: For fetching mcx data
Author: Tapan Hazarika
9 changes: 9 additions & 0 deletions mcxpy.egg-info/SOURCES.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
setup.py
mcxpy/__init__.py
mcxpy/__init__.pyi
mcxpy/mcx.py
mcxpy/py.typed
mcxpy.egg-info/PKG-INFO
mcxpy.egg-info/SOURCES.txt
mcxpy.egg-info/dependency_links.txt
mcxpy.egg-info/top_level.txt
1 change: 1 addition & 0 deletions mcxpy.egg-info/dependency_links.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@

1 change: 1 addition & 0 deletions mcxpy.egg-info/top_level.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
mcxpy
11 changes: 11 additions & 0 deletions setup.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
from setuptools import setup

setup(
name='mcxpy',
version='0.0.1',
description='For fetching mcx data',
author='Tapan Hazarika',
packages=['mcxpy'],
package_data={'mcxpy': ['py.typed', '__init__.pyi', 'mcxpy.pyi']}
)

0 comments on commit 02fe943

Please sign in to comment.