108 Commits

Author SHA1 Message Date
wanyaokun 42a1bfe4d7 修改生成问题的提示词 2024-09-24 17:56:20 +08:00
wanyaokun aace9ce292 修改属性图节点的层级结构,新增子父级关系 2024-09-24 17:11:20 +08:00
wanyaokun e0fc5381d8 更新文件名称 2024-09-24 09:52:24 +08:00
wanyaokun 4ab7941fe0 新增openai的向量,重排模型 2024-09-22 13:19:58 +08:00
wanyaokun f7260da6d9 优化属性图检索功能及支持OpenAI线上模型 2024-09-20 17:34:38 +08:00
wanyaokun 092f7230c1 修改GraphRAG缺陷 2024-09-19 11:38:35 +08:00
wanyaokun 03586a9b0d 修改答题文件格式问题 2024-09-18 10:30:58 +08:00
wanyaokun f2df0d894a 修改库依赖 2024-09-18 09:21:48 +08:00
wanyaokun 67b1959d80 将属性图流程同步至主流程中 2024-09-14 16:35:46 +08:00
wanyaokun 6de6cc201e 修改文件结构 2024-09-14 15:45:12 +08:00
wanyaokun a532b642f4 删除错误工程 2024-09-14 14:28:40 +08:00
wanyaokun c45462354e 修改数据格式 2024-09-14 14:22:40 +08:00
wanyaokun eb9f590571 新增架线南网数据 2024-09-14 12:06:24 +08:00
wanyaokun 0720c6dfcd 新增工程数据 2024-09-14 11:23:36 +08:00
wanyaokun 2b17e44120 漏传文件 2024-09-14 09:51:11 +08:00
wanyaokun a8f99adaca 新增属性图的配置 2024-09-14 09:49:51 +08:00
wanyaokun df7ebf3d4f 新增属性图谱 2024-09-14 09:44:43 +08:00
wanyaokun e18e4f22db 调整问题生成的提示词 2024-09-12 16:49:55 +08:00
wanyaokun c262aec6bd 新增单元测试 2024-09-12 13:58:42 +08:00
wanyaokun 47437044cb 新增自定义节点元数据回调函数 2024-09-10 15:30:58 +08:00
wanyaokun 5edfecef30 修改模型名称 2024-09-10 15:07:16 +08:00
wanyaokun f4b1f40173 自定义重排类,实现分数阈值过滤 2024-09-10 15:05:12 +08:00
wanyaokun 0bf2799acf Merge branch 'dev-web' of https://git.97id.com/ly/zjdataai-app into dev-web 2024-09-10 14:42:17 +08:00
wanyaokun 0fe60a7963 自定义xinfeng接口 2024-09-10 14:39:51 +08:00
ly a66ba3c48e 更新项目依赖关系 2024-09-10 14:19:51 +08:00
wanyaokun a165d55822 更新LlamaIndex版本库 2024-09-10 14:07:52 +08:00
ly 6f5548ee61 修改获取文件名称方法 2024-09-10 10:17:28 +08:00
ly 331595cc57 Merge branch 'dev-web' of https://git.97id.com/ly/zjdataai-app into dev-web 2024-09-10 10:12:47 +08:00
wanyaokun cb34fde995 工程名称下拉项获取兼容.md文件,同时新增自定义答案合成类 2024-09-10 09:59:00 +08:00
ly 123693c9a0 Merge branch 'dev-web' of https://git.97id.com/ly/zjdataai-app into dev-web 2024-09-10 08:43:38 +08:00
ly a897f0c6de 更新项目依赖环境支持 2024-09-10 08:42:37 +08:00
ly adce2a3809 更新xinference支持 2024-09-10 08:42:12 +08:00
ly 7875e2cbcc 修改提示词 2024-09-10 08:40:54 +08:00
ly 95fbc820b9 由于xinference 0.15.0 最新版已解决和llamaindex 0.2.0版本的冲突问题,所以无需自己实现embeddings和rerank。 2024-09-10 08:38:57 +08:00
wanyaokun 54f19a20fc 调整MarkDown文件读取的格式内容 2024-09-09 19:10:16 +08:00
wanyaokun bc124c5513 新增MarkDown切片 2024-09-06 18:22:01 +08:00
wanyaokun 1c773924db 解决模块嵌套问题 2024-09-06 16:35:34 +08:00
wanyaokun 60b0f11ca2 新增ollama重排类 2024-09-06 10:07:22 +08:00
wanyaokun 21fdc16259 更新环境配置 2024-09-06 08:47:53 +08:00
wanyaokun 64ba7efcdc 修改答案合成的策略 2024-09-06 08:23:17 +08:00
wanyaokun 9a09e9f79f 误删除文件 2024-09-05 18:20:35 +08:00
wanyaokun 9ac53011e0 关键词检索增加容错 2024-09-05 18:16:54 +08:00
wanyaokun f171282a0c 修改关键词检索溢出问题 2024-09-05 18:13:39 +08:00
wanyaokun 626ff1e632 修改提示词错误问题 2024-09-05 15:39:57 +08:00
ly 5189d4368f 调整查询工具级的提示词内容及提示词内容 2024-09-05 12:50:12 +08:00
ly 5f182075aa 暂时去小查询引擎的流式输出功能,因为此模式下获取不到原 2024-09-05 12:49:47 +08:00
ly b1ef410638 修改文件编码类型为UTF8 2024-09-05 12:48:26 +08:00
ly 7b040ae248 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev-web 2024-09-05 12:35:21 +08:00
ly 7023b54246 解决xinference内嵌模型类使用问题。由于目前xinference组件的版本和llamaindex最新版有冲突,所以未更新支持xinference的内嵌模型的版本 2024-09-05 12:12:31 +08:00
ly aee6aa3c04 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-09-05 11:36:53 +08:00
wanyaokun 786c4d05f6 解决冲突 2024-09-05 10:50:31 +08:00
wanyaokun a8db51e844 新增工程信息下拉项 2024-09-05 10:45:07 +08:00
ly 545fbc732b 合并冲突报错 2024-09-05 10:35:28 +08:00
ly 56cb36dfc9 调整提示词位置 2024-09-05 10:35:14 +08:00
ly a6c5988408 去除 main.py 导入的无用的llamaindex导入 2024-09-05 10:34:41 +08:00
ly c4cf09a28f Merge branch 'dev' into dev-web 2024-09-05 10:11:35 +08:00
ly 75fde3598b Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-09-05 10:11:10 +08:00
wanyaokun aba6475c5a 将事件名称转义成中文及优化关键字检索 2024-09-05 09:24:35 +08:00
wanyaokun ae19725d72 修改模型参数 2024-09-05 09:01:27 +08:00
wanyaokun 97a486e631 优化模型初始化代码 2024-09-04 15:00:38 +08:00
wanyaokun 728ee06c5a 支持节点元数据输出及代码优化,减少事件重复添加 2024-09-02 19:58:18 +08:00
wanyaokun a4dd385368 修改缺陷:获取会话时未记录选择的工程信息 2024-09-02 09:26:26 +08:00
wanyaokun 24c808d66d 修改反馈取消时异常问题 2024-09-02 08:49:32 +08:00
wanyaokun ced3199550 新增工程数据 2024-08-30 19:12:40 +08:00
chentianrui 680e24c516 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-30 18:40:32 +08:00
chentianrui 6663ee8976 新增加了单元测试 2024-08-30 18:40:21 +08:00
wanyaokun c4088fe963 提交配置文件 2024-08-30 16:45:39 +08:00
wanyaokun e7628809ad 新增工程信息、检索的知识片段节点回传、下一轮建议问题列表 2024-08-30 16:42:36 +08:00
wanyaokun 73565b26e4 合并Dev分支代码 2024-08-30 10:49:05 +08:00
ly 0a5f335981 调整NLTK数据目录和JIEBA字典位置到本项目中,避免重新安装时需要从网上下载 2024-08-30 01:20:29 +08:00
ly 2901bd9eaf 优化导入,解决初始化LLAMAINDEX过程中环境变量没起作用问题 2024-08-30 01:16:35 +08:00
ly 453b3ca55c Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-30 00:00:57 +08:00
wanyaokun 03c4eb1af1 优化ChatCallbackEvent事件代码 2024-08-29 19:52:53 +08:00
wanyaokun 480a1f7fdc 新增工程配置信息 2024-08-29 19:03:38 +08:00
wanyaokun cdc9d84a1e Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-29 19:01:40 +08:00
wanyaokun 50f35bb0c9 优化Web事件代码 2024-08-29 19:00:25 +08:00
chentianrui 4a8c79e83d 参数优化针对问题做出了调整 2024-08-29 15:09:55 +08:00
ly f0afd1a4bb Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-29 12:03:28 +08:00
chentianrui de34c3938c 增加了参数评估 2024-08-29 12:02:53 +08:00
ly eb572eff27 增加加载环境变量功能 2024-08-29 11:54:20 +08:00
chentianrui 2706cf9d5a 更新了依赖包 2024-08-29 11:41:42 +08:00
chentianrui 5fa4752d6e Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-29 11:39:06 +08:00
chentianrui aff1793c4e 新增了参数评估脚本和评分脚本 2024-08-29 11:38:45 +08:00
ly 0db159ac89 增加新的前端子模块 2024-08-29 10:48:40 +08:00
ly 131d6ef1d1 完善接口,实现对DIFY前端消息流传输的支持 2024-08-29 08:26:59 +08:00
wanyaokun e9ccd7db35 合并代码 2024-08-28 20:02:15 +08:00
wanyaokun 4020b603b1 合并代码 2024-08-28 19:58:37 +08:00
chentianrui 3ee1ba529f Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-28 18:12:37 +08:00
chentianrui 576a2ae737 增加了评估脚本 2024-08-28 18:12:28 +08:00
ly 9b47e1a6e1 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-28 17:41:52 +08:00
wanyaokun 20510a937b Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-28 17:38:43 +08:00
wanyaokun a7c79df339 修改web请求接口 2024-08-28 17:35:28 +08:00
chentianrui 327bba75d5 修改了语句错误 2024-08-28 17:24:55 +08:00
chentianrui d1242d2080 修改了从数据库中查找取费表和工程量表,新加了一个树状搜索总结搜索引擎 2024-08-28 14:46:13 +08:00
ly 0f09551f5d Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-28 11:49:22 +08:00
chentianrui 8a5facb5b6 增加了判断是否使用数据库 2024-08-28 09:45:01 +08:00
chentianrui 0f7c900c1e 更改了提示词 2024-08-28 09:42:12 +08:00
chentianrui b008ad9766 更改了提示词 2024-08-28 09:39:57 +08:00
ly 56459c164e 配置文件增加UTF8编码格式支持,以免解析中文时出现问题 2024-08-28 08:04:01 +08:00
wanyaokun 07a3b2a147 修改POST和Get请求代码 2024-08-27 17:48:38 +08:00
ly b4c571cddb 增加对接DIFY前端支持功能 2024-08-27 08:43:00 +08:00
ly 7068b058e8 调整文件格式为DOCX 2024-08-27 08:40:46 +08:00
wanyaokun 33b2281b7b 修改ID为空的问题 2024-08-26 20:16:58 +08:00
wanyaokun 1704b61609 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-26 19:58:57 +08:00
wanyaokun afccaf6eb5 新增Web前后端通信代码 2024-08-26 19:57:22 +08:00
ly b052d373f1 删除误上传的文件 2024-08-26 09:54:33 +08:00
ly 7462244f01 Merge branch 'dev' of https://git.97id.com/ly/zjdataai-app into dev 2024-08-26 09:01:26 +08:00
ly 2b64aca26b 修改文件格式,因为默认不支持doc格式。 2024-08-23 16:57:27 +08:00
178 changed files with 364500 additions and 5962 deletions
+3
View File
@@ -0,0 +1,3 @@
[submodule "webapp"]
path = webapp
url = https://git.97id.com/ly/webapp.git
+91 -22
View File
@@ -2,35 +2,83 @@
# LLAMA_CLOUD_API_KEY=
SQL_DATABASE_URL=mysql+pymysql://zjinfo1:Dy2Bcr53Hm5xRkba@110.42.234.166:3306/zjinfo1
#SQL_DATABASE_URL=mysql+pymysql://zjinfo2:GSKcziSdBixDXwcd@110.42.234.166:3306/zjinfo2
SQLITE_DATABASE_URL=sqlite:///./source.db
DASHSCOPE_API_KEY=sk-02c8540e86d84b7ca0e6f4f51bac6e60
# The provider for the AI models to use.
MODEL_PROVIDER=dashscope
# The name of LLM model to use.
MODEL=qwen-max
# The number of similar embeddings to return when retrieving documents.
TOP_K=10
#--------------------------
# 是否启用混合检索
HYBRID_ENABLED = true
# 混合检索阈值
HYBRID_ALPHA = 0.6
# 是否启用检索重排功能
ENABLE_RERANK=true
# Name of the embedding model to use.
EMBEDDING_MODEL=text-embedding-v2
RERANK_ENABLED=true
# Dimension of the embedding model to use.
#---------- rerank- Xinference ----------------
#RERANK_PROVIDER=xinference
#RERANK_MODEL=bge-reranker-v2-m3
#RERANK_BASE_URL=http://10.1.16.39:9995
#RERANK_TOP_N=5
#RERANK_THRESHOLD=0.3
#---------- rerank- ollama ----------------
RERANK_PROVIDER=ollama
RERANK_MODEL= /models/bge-reranker-base
RERANK_TOP_N=5
RERANK_THRESHOLD=0.3
#---------- model - Xinference ----------------
#MODEL_PROVIDER=xinference
#OPENAI_API_KEY=xinference
#BASE_URL=http://172.20.0.145:9995
#MODEL=Qwen2-72B-Instruct-GPTQ-Int8
## Temperature for sampling from the model.
#LLM_TEMPERATURE=0.1
#---------- model - dashscope ----------------
MODEL_PROVIDER=dashscope
DASHSCOPE_API_KEY=sk-221d2d202e104618a56002ce2e7dc0d0
MODEL=qwen2-math-72b-instruct
# #---------- model - openai ----------------
MODEL_PROVIDER=openai
OPENAI_API_KEY=
BASE_URL=https://api.siliconflow.cn/v1
MODEL=alibaba/Qwen1.5-110B-Chat
LLM_TEMPERATURE=0.1
CONTEXT_WINDOW = 8192
IS_CHAT_MODEL = true
IS_FUN_CALL_MODEL = false
#---------- embedding - openai ----------------
EMBEDDING_PROVIDER=openai
OPENAI_API_KEY=
EMBEDDING_MODEL=BAAI/bge-m3
EMBEDDING_BASE_URL=https://api.siliconflow.cn/v1
EMBEDDING_DIM=1024
RERANK_PROVIDER=openai
OPENAI_API_KEY=sk-hhoqttvhibirwheyponjifsqwssgxotoqlcjufkidytwxngi
RERANK_MODEL=BAAI/bge-reranker-v2-m3
RERANK_BASE_URL=https://api.siliconflow.cn/v1
RERANK_TOP_N=5
#---------- embedding - Xinference ----------------
#EMBEDDING_PROVIDER=xinference
#EMBEDDING_MODEL=bge-m3
#EMBEDDING_BASE_URL=http://10.1.16.39:9995
#EMBEDDING_DIM=1024
---------- embedding - dashscope ----------------
EMBEDDING_PROVIDER=dashscope
EMBEDDING_MODEL=text-embedding-v1
# The questions to help users get started (multi-line).
CONVERSATION_STARTERS=本工程指什么?\n总算表有哪些费用?\n项目划分哪些内容构成?\n其他费用表有哪些内容?
# The OpenAI API key to use.
# OPENAI_API_KEY=
# Temperature for sampling from the model.
# LLM_TEMPERATURE=
# Maximum number of tokens to generate.
# LLM_MAX_TOKENS=
# The number of similar embeddings to return when retrieving documents.
TOP_K=5
# The time in milliseconds to wait for the stream to return a response.
STREAM_TIMEOUT=60000
@@ -39,6 +87,17 @@ VECTOR_STORE_TYPE=chroma
# The name of the collection in your vector database
VECTOR_STORE_COLLECTION=default
#模型查询方式:graph、rag
LLM_QUERY_WAY = graph
#属性图存储类型:本地属性图库(默认),neo4j
GRAPH_STORE_TYPE =
#---------- neo4j - PropertyGraph ----------------
NEO4J_USERNAME = neo4j
NEO4J_PASSWORD = neo4j
NEO4J_URL = bolt://10.1.6.40:7687
# The API endpoint for your vector database
# VECTOR_STORE_HOST=
@@ -50,7 +109,7 @@ VECTOR_STORE_COLLECTION=default
# Otherwise, use VECTOR_STORE__HOST and VECTOR_STORE__PORT config above
VECTOR_STORE_PATH=./storage_vector
BM_RETRIEVER_PATH =./storage_bm
GRAPH_STORAGE_PATH =./storage_graph
PHOENIX_API_KEY=123456
@@ -79,3 +138,13 @@ SYSTEM_PROMPT="You are a weather forecast agent. You help users to get the weath
- You can install any pip package (if it exists) by running a cell with pip install.
"
PRJTOJSON_URL = 'http://10.1.6.60:8092'
PROJECT_TITLE = "您好,我是博微工程理解小助手,您可以问我有关[线路工程]工程数据的相关问题!"
CHAT_UPLOAD_FILECACHE = "./output/uploaded"
JIEBA_DATA=./nltk_data
NLTK_DATA=./nltk_data
#IO流默认的编码格式
PYTHONUTF8=1
+24 -13
View File
@@ -1,7 +1,13 @@
JIEBA_DATA=./nltk_data
NLTK_DATA=./nltk_data
SQLITE_DATABASE_URL=sqlite:///./source.db
DATA_SOURCE_CACHE=./restapi
# The Llama Cloud API key.
# LLAMA_CLOUD_API_KEY=
SQL_DATABASE_URL=mysql+pymysql://zjinfo1:Dy2Bcr53Hm5xRkba@110.42.234.166:3306/zjinfo1
#SQL_DATABASE_URL=mysql+pymysql://zjinfo2:GSKcziSdBixDXwcd@110.42.234.166:3306/zjinfo2
SQLITE_DATABASE_URL=sqlite:///./source.db
# The number of similar embeddings to return when retrieving documents.
TOP_K=10
@@ -13,27 +19,28 @@ HYBRID_ALPHA = 0.6
#--------------------------
# 是否启用检索重排功能
RERANK_ENABLED=true
# Rerank model
#---------- rerank- Xinference ----------------
RERANK_PROVIDER=xinference
RERANK_MODEL=bge-reranker-v2-m3
RERANK_BASE_URL=http://10.1.16.39:9995
RERANK_TOP_N=5
RERANK_THRESHOLD=0.3
#---------- Xinference ----------------
# The provider for the AI models to use.
MODEL_PROVIDER=xinference
# The OpenAI API key to use.
OPENAI_API_KEY=xinference
#---------- model - Xinference ----------------
MODEL_PROVIDER=xinference # The provider for the AI models to use.
OPENAI_API_KEY=xinference # The OpenAI API key to use.
BASE_URL=http://10.1.0.142:9995
MODEL=Qwen2-72B-Instruct-GPTQ-Int8
# Temperature for sampling from the model.
LLM_TEMPERATURE=0.1
# Maximum number of tokens to generate.
#LLM_MAX_TOKENS=
# Name of the embedding model to use.
LLM_TEMPERATURE=0.1 # Temperature for sampling from the model.
#LLM_MAX_TOKENS= # Maximum number of tokens to generate.
#---------- embedding - Xinference ----------------
EMBEDDING_PROVIDER=xinference
EMBEDDING_MODEL=bge-m3
EMBEDDING_BASE_URL=http://10.1.16.39:9995
# Dimension of the embedding model to use.
EMBEDDING_DIM=1024
EMBEDDING_DIM=1024 # Dimension of the embedding model to use.
##---------- OpenAI ----------------
## The provider for the AI models to use.
@@ -110,3 +117,7 @@ SYSTEM_PROMPT="You are a weather forecast agent. You help users to get the weath
- You can install any pip package (if it exists) by running a cell with pip install.
"
PRJTOJSON_URL = 'http://10.1.6.60:8092'
PROJECT_TITLE = "您好,我是博微工程理解小助手,您可以问我有关[线路工程]工程数据的相关问题!"
CHAT_UPLOAD_FILECACHE = "./output/uploaded"
@@ -1,61 +0,0 @@
from llama_index.embeddings.openai import OpenAIEmbedding
from llama_index.core.settings import Settings
from typing import Dict
import os
DEFAULT_MODEL = "gpt-3.5-turbo"
DEFAULT_EMBEDDING_MODEL = "text-embedding-3-large"
class TSIEmbedding(OpenAIEmbedding):
def __init__(self, **kwargs):
super().__init__(**kwargs)
self._query_engine = self._text_engine = self.model_name
def llm_config_from_env() -> Dict:
from llama_index.core.constants import DEFAULT_TEMPERATURE
model = os.getenv("MODEL", DEFAULT_MODEL)
temperature = os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)
max_tokens = os.getenv("LLM_MAX_TOKENS")
api_key = os.getenv("T_SYSTEMS_LLMHUB_API_KEY")
api_base = os.getenv("T_SYSTEMS_LLMHUB_BASE_URL")
config = {
"model": model,
"api_key": api_key,
"api_base": api_base,
"temperature": float(temperature),
"max_tokens": int(max_tokens) if max_tokens is not None else None,
}
return config
def embedding_config_from_env() -> Dict:
from llama_index.core.constants import DEFAULT_EMBEDDING_DIM
model = os.getenv("EMBEDDING_MODEL", DEFAULT_EMBEDDING_MODEL)
dimension = os.getenv("EMBEDDING_DIM", DEFAULT_EMBEDDING_DIM)
api_key = os.getenv("T_SYSTEMS_LLMHUB_API_KEY")
api_base = os.getenv("T_SYSTEMS_LLMHUB_BASE_URL")
config = {
"model_name": model,
"dimension": int(dimension) if dimension is not None else None,
"api_key": api_key,
"api_base": api_base,
}
return config
def init_llmhub():
from llama_index.llms.openai_like import OpenAILike
llm_configs = llm_config_from_env()
embedding_configs = embedding_config_from_env()
Settings.embed_model = TSIEmbedding(**embedding_configs)
Settings.llm = OpenAILike(
**llm_configs,
is_chat_model=True,
is_function_calling_model=False,
context_window=4096,
)
@@ -1,20 +0,0 @@
import os
import llama_index.core
def init_observability():
PHOENIX_API_KEY = os.getenv("PHOENIX_API_KEY")
if not PHOENIX_API_KEY:
raise ValueError("PHOENIX_API_KEY environment variable is not set")
os.environ["OTEL_EXPORTER_OTLP_HEADERS"] = f"api_key={PHOENIX_API_KEY}"
PHOENIX_URL = os.getenv("PHOENIX_URL")
llama_index.core.set_global_handler(
"arize_phoenix", endpoint=PHOENIX_URL, eval_params={}
)
#debugHandle=[]
# llama_debug = LlamaDebugHandler(print_trace_on_end=True)
# debugHandle.append(llama_debug)
# callback_manager = CallbackManager(debugHandle)
# settings.Settings.callback_manager = callback_manager
@@ -1,235 +0,0 @@
import os
from typing import Dict
from llama_index.core.constants import DEFAULT_TEMPERATURE
from llama_index.core.settings import Settings
from llama_index.llms.xinference import Xinference
from llama_index.llms.xinference.base import DEFAULT_XINFERENCE_TEMP
from app.xinference.base import XinferenceEmbedding, XinferenceRerank
def get_node_postprocessors():
rerank_enabled = os.getenv("RERANK_ENABLED").title()
if rerank_enabled is None or rerank_enabled == 'False':
return []
rerank_model = os.getenv("RERANK_MODEL")
rerank_url = os.getenv("RERANK_BASE_URL")
rerank_top_n = os.getenv("RERANK_TOP_N")
rerank_threshold = os.getenv("RERANK_THRESHOLD")
postprocess = None
if rerank_model is not None:
postprocess = [XinferenceRerank(rerank_model, rerank_url, top_n=rerank_top_n, threshold=rerank_threshold)]
return postprocess
def init_settings():
model_provider = os.getenv("MODEL_PROVIDER")
match model_provider:
case "openai":
init_openai()
case "dashscope":
init_dashscope()
case "groq":
init_groq()
case "ollama":
init_ollama()
case "anthropic":
init_anthropic()
case "gemini":
init_gemini()
case "mistral":
init_mistral()
case "azure-openai":
init_azure_openai()
case "t-systems":
from .llmhub import init_llmhub
init_llmhub()
case "xinference":
init_xinference()
case _:
raise ValueError(f"Invalid model provider: {model_provider}")
Settings.chunk_size = int(os.getenv("CHUNK_SIZE", "1024"))
Settings.chunk_overlap = int(os.getenv("CHUNK_OVERLAP", "20"))
def init_ollama():
# from llama_index.embeddings.ollama import OllamaEmbedding
# from llama_index.llms.ollama.base import DEFAULT_REQUEST_TIMEOUT, Ollama
#
# base_url = os.getenv("OLLAMA_BASE_URL") or "http://127.0.0.1:11434"
# request_timeout = float(
# os.getenv("OLLAMA_REQUEST_TIMEOUT", DEFAULT_REQUEST_TIMEOUT)
# )
# Settings.embed_model = OllamaEmbedding(
# base_url=base_url,
# model_name=os.getenv("EMBEDDING_MODEL"),
# )
# Settings.llm = Ollama(
# base_url=base_url, model=os.getenv("MODEL"), request_timeout=request_timeout
# )
pass
def init_xinference():
base_url = os.getenv("BASE_URL")
model = os.getenv("MODEL")
max_tokens = int(os.getenv("LLM_MAX_TOKENS")) if os.getenv("LLM_MAX_TOKENS") is not None else None
temperature = float(os.getenv("LLM_TEMPERATURE", DEFAULT_XINFERENCE_TEMP))
Settings.llm = Xinference(model, base_url, temperature, max_tokens)
embedding_base_url = os.getenv("EMBEDDING_BASE_URL")
embedding_base_url = embedding_base_url if embedding_base_url != None and embedding_base_url != "" else base_url
embed_model_name = os.getenv("EMBEDDING_MODEL")
dimensions = os.getenv("EMBEDDING_DIM")
dimensions = int(dimensions) if dimensions is not None else None
Settings.embed_model = XinferenceEmbedding(embed_model_name, embedding_base_url, dimensions=dimensions)
def init_openai():
from llama_index.core.constants import DEFAULT_TEMPERATURE
from llama_index.embeddings.openai import OpenAIEmbedding
from llama_index.llms.openai import OpenAI
max_tokens = os.getenv("LLM_MAX_TOKENS")
config = {
"model": os.getenv("MODEL"),
"temperature": float(os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)),
"max_tokens": int(max_tokens) if max_tokens is not None else None,
}
Settings.llm = OpenAI(**config)
dimensions = os.getenv("EMBEDDING_DIM")
config = {
"model": os.getenv("EMBEDDING_MODEL"),
"dimensions": int(dimensions) if dimensions is not None else None,
}
Settings.embed_model = OpenAIEmbedding(**config)
def init_dashscope():
from llama_index.llms.dashscope import DashScope,DashScopeGenerationModels
from llama_index.embeddings.dashscope import DashScopeEmbedding,DashScopeBatchTextEmbeddingModels,DashScopeTextEmbeddingType,DashScopeTextEmbeddingModels
max_tokens = os.getenv("LLM_MAX_TOKENS")
config = {
"model": os.getenv("MODEL"),
"temperature": float(os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)),
"max_tokens": int(max_tokens) if max_tokens is not None else None,
}
Settings.llm = llm = DashScope(model_name=DashScopeGenerationModels.QWEN_MAX)
dimensions = os.getenv("EMBEDDING_DIM")
config = {
"model": os.getenv("EMBEDDING_MODEL"),
"dimensions": int(dimensions) if dimensions is not None else None,
}
Settings.embed_model = DashScopeEmbedding(model_name=DashScopeTextEmbeddingModels.TEXT_EMBEDDING_V2,
text_type=DashScopeTextEmbeddingType.TEXT_TYPE_QUERY)
def init_azure_openai():
# from llama_index.core.constants import DEFAULT_TEMPERATURE
# from llama_index.embeddings.azure_openai import AzureOpenAIEmbedding
# from llama_index.llms.azure_openai import AzureOpenAI
#
# llm_deployment = os.environ["AZURE_OPENAI_LLM_DEPLOYMENT"]
# embedding_deployment = os.environ["AZURE_OPENAI_EMBEDDING_DEPLOYMENT"]
# max_tokens = os.getenv("LLM_MAX_TOKENS")
# temperature = os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)
# dimensions = os.getenv("EMBEDDING_DIM")
#
# azure_config = {
# "api_key": os.environ["AZURE_OPENAI_KEY"],
# "azure_endpoint": os.environ["AZURE_OPENAI_ENDPOINT"],
# "api_version": os.getenv("AZURE_OPENAI_API_VERSION")
# or os.getenv("OPENAI_API_VERSION"),
# }
#
# Settings.llm = AzureOpenAI(
# model=os.getenv("MODEL"),
# max_tokens=int(max_tokens) if max_tokens is not None else None,
# temperature=float(temperature),
# deployment_name=llm_deployment,
# **azure_config,
# )
#
# Settings.embed_model = AzureOpenAIEmbedding(
# model=os.getenv("EMBEDDING_MODEL"),
# dimensions=int(dimensions) if dimensions is not None else None,
# deployment_name=embedding_deployment,
# **azure_config,
# )
pass
def init_fastembed():
"""
Use Qdrant Fastembed as the local embedding provider.
"""
# from llama_index.embeddings.fastembed import FastEmbedEmbedding
#
# embed_model_map: Dict[str, str] = {
# # Small and multilingual
# "all-MiniLM-L6-v2": "sentence-transformers/all-MiniLM-L6-v2",
# # Large and multilingual
# "paraphrase-multilingual-mpnet-base-v2": "sentence-transformers/paraphrase-multilingual-mpnet-base-v2", # noqa: E501
# }
#
# # This will download the model automatically if it is not already downloaded
# Settings.embed_model = FastEmbedEmbedding(
# model_name=embed_model_map[os.getenv("EMBEDDING_MODEL")]
# )
pass
def init_groq():
# from llama_index.llms.groq import Groq
#
# model_map: Dict[str, str] = {
# "llama3-8b": "llama3-8b-8192",
# "llama3-70b": "llama3-70b-8192",
# "mixtral-8x7b": "mixtral-8x7b-32768",
# }
#
# Settings.llm = Groq(model=model_map[os.getenv("MODEL")])
# # Groq does not provide embeddings, so we use FastEmbed instead
# init_fastembed()
pass
def init_anthropic():
# from llama_index.llms.anthropic import Anthropic
#
# model_map: Dict[str, str] = {
# "claude-3-opus": "claude-3-opus-20240229",
# "claude-3-sonnet": "claude-3-sonnet-20240229",
# "claude-3-haiku": "claude-3-haiku-20240307",
# "claude-2.1": "claude-2.1",
# "claude-instant-1.2": "claude-instant-1.2",
# }
#
# Settings.llm = Anthropic(model=model_map[os.getenv("MODEL")])
# # Anthropic does not provide embeddings, so we use FastEmbed instead
# init_fastembed()
pass
def init_gemini():
# from llama_index.embeddings.gemini import GeminiEmbedding
# from llama_index.llms.gemini import Gemini
#
# model_name = f"models/{os.getenv('MODEL')}"
# embed_model_name = f"models/{os.getenv('EMBEDDING_MODEL')}"
#
# Settings.llm = Gemini(model=model_name)
# Settings.embed_model = GeminiEmbedding(model_name=embed_model_name)
pass
def init_mistral():
# from llama_index.embeddings.mistralai import MistralAIEmbedding
# from llama_index.llms.mistralai import MistralAI
#
# Settings.llm = MistralAI(model=os.getenv("MODEL"))
# Settings.embed_model = MistralAIEmbedding(model_name=os.getenv("EMBEDDING_MODEL"))
pass
@@ -1,150 +0,0 @@
import logging
import os
from typing import List
from fastapi import APIRouter, BackgroundTasks, Depends, HTTPException, Request, status
from llama_index.core.chat_engine.types import BaseChatEngine, NodeWithScore
from llama_index.core.llms import MessageRole
from llama_index.core.vector_stores.types import MetadataFilter, MetadataFilters
from app.api.routers.events import EventCallbackHandler
from app.api.routers.models import (
ChatConfig,
ChatData,
Message,
Result,
SourceNodes,
)
from app.api.routers.vercel_response import VercelStreamResponse
from app.api.services.llama_cloud import LLamaCloudFileService
from app.engine import get_chat_engine
chat_router = r = APIRouter()
logger = logging.getLogger("uvicorn")
def process_response_nodes(
nodes: List[NodeWithScore],
background_tasks: BackgroundTasks,
):
"""
Start background tasks on the source nodes if needed.
"""
files_to_download = SourceNodes.get_download_files(nodes)
for file in files_to_download:
background_tasks.add_task(
LLamaCloudFileService.download_llamacloud_pipeline_file, file
)
# streaming endpoint - delete if not needed
@r.post("")
async def chat(
request: Request,
data: ChatData,
background_tasks: BackgroundTasks,
chat_engine: BaseChatEngine = Depends(get_chat_engine),
):
try:
last_message_content = data.get_last_message_content()
# 由于基于历史消息的提示词没有调整好,所以暂时屏蔽历史消息
data.messages.clear()
messages = data.get_history_messages()
doc_ids = data.get_chat_document_ids()
filters = generate_filters(doc_ids)
params = data.data or {}
logger.info("Creating chat engine with filters", filters.dict())
chat_engine = get_chat_engine(filters=filters, params=params)
event_handler = EventCallbackHandler()
chat_engine.callback_manager.handlers.append(event_handler) # type: ignore
response = await chat_engine.astream_chat(last_message_content, messages)
process_response_nodes(response.source_nodes, background_tasks)
return VercelStreamResponse(request, event_handler, response, data)
except Exception as e:
logger.exception("Error in chat engine", exc_info=True)
raise HTTPException(
status_code=status.HTTP_500_INTERNAL_SERVER_ERROR,
detail=f"Error in chat engine: {e}",
) from e
def generate_filters(doc_ids):
if len(doc_ids) > 0:
filters = MetadataFilters(
filters=[
MetadataFilter(
key="private",
value=["true"],
operator="nin", # type: ignore
),
MetadataFilter(
key="doc_id",
value=doc_ids,
operator="in", # type: ignore
),
],
condition="or", # type: ignore
)
else:
filters = MetadataFilters(
# Use the "NIN" - "not in" operator to include all public documents (don't have the private key set)
filters=[
MetadataFilter(
key="private",
value=["true"],
operator="nin", # type: ignore
),
]
)
return filters
# non-streaming endpoint - delete if not needed
@r.post("/request")
async def chat_request(
data: ChatData,
chat_engine: BaseChatEngine = Depends(get_chat_engine),
) -> Result:
last_message_content = data.get_last_message_content()
messages = data.get_history_messages()
response = await chat_engine.achat(last_message_content, messages)
return Result(
result=Message(role=MessageRole.ASSISTANT, content=response.response),
nodes=SourceNodes.from_source_nodes(response.source_nodes),
)
@r.get("/config")
async def chat_config() -> ChatConfig:
starter_questions = None
conversation_starters = os.getenv("CONVERSATION_STARTERS")
if conversation_starters and conversation_starters.strip():
starter_questions = conversation_starters.strip().split("\\n")
return ChatConfig(starter_questions=starter_questions)
@r.get("/config/llamacloud")
async def chat_llama_cloud_config():
projects = LLamaCloudFileService.get_all_projects_with_pipelines()
pipeline = os.getenv("LLAMA_CLOUD_INDEX_NAME")
project = os.getenv("LLAMA_CLOUD_PROJECT_NAME")
pipeline_config = (
pipeline
and project
and {
"pipeline": pipeline,
"project": project,
}
or None
)
return {
"projects": projects,
"pipeline": pipeline_config,
}
@@ -1,149 +0,0 @@
import json
import asyncio
import logging
from typing import AsyncGenerator, Dict, Any, List, Optional
from llama_index.core.callbacks.base import BaseCallbackHandler
from llama_index.core.callbacks.schema import CBEventType
from llama_index.core.tools.types import ToolOutput
from pydantic import BaseModel
logger = logging.getLogger(__name__)
class CallbackEvent(BaseModel):
event_type: CBEventType
payload: Optional[Dict[str, Any]] = None
event_id: str = ""
def get_retrieval_message(self) -> dict | None:
if self.payload:
nodes = self.payload.get("nodes")
if nodes:
msg = f"根据查询检索到 {len(nodes)} 源文件"
else:
msg = f"查询检索中: '{self.payload.get('query_str')}'"
return {
"type": "events",
"data": {"title": msg},
}
else:
return None
def get_tool_message(self) -> dict | None:
func_call_args = self.payload.get("function_call")
if func_call_args is not None and "tool" in self.payload:
tool = self.payload.get("tool")
return {
"type": "events",
"data": {
"title": f"调用工具 {tool.name} ,参数: {func_call_args}",
},
}
def _is_output_serializable(self, output: Any) -> bool:
try:
json.dumps(output)
return True
except TypeError:
return False
def get_agent_tool_response(self) -> dict | None:
response = self.payload.get("response")
if response is not None:
sources = response.sources
for source in sources:
# Return the tool response here to include the toolCall information
if isinstance(source, ToolOutput):
if self._is_output_serializable(source.raw_output):
output = source.raw_output
else:
output = source.content
return {
"type": "tools",
"data": {
"toolOutput": {
"output": output,
"isError": source.is_error,
},
"toolCall": {
"id": None, # There is no tool id in the ToolOutput
"name": source.tool_name,
"input": source.raw_input,
},
},
}
def to_response(self):
try:
match self.event_type:
case "retrieve":
return self.get_retrieval_message()
case "function_call":
return self.get_tool_message()
case "agent_step":
return self.get_agent_tool_response()
case _:
return None
except Exception as e:
logger.error(f"转换回应时间时发生错误,原因: {e}")
return None
class EventCallbackHandler(BaseCallbackHandler):
_aqueue: asyncio.Queue
is_done: bool = False
def __init__(
self,
):
"""Initialize the base callback handler."""
ignored_events = [
CBEventType.CHUNKING,
CBEventType.NODE_PARSING,
CBEventType.EMBEDDING,
CBEventType.LLM,
CBEventType.TEMPLATING,
]
super().__init__(ignored_events, ignored_events)
self._aqueue = asyncio.Queue()
def on_event_start(
self,
event_type: CBEventType,
payload: Optional[Dict[str, Any]] = None,
event_id: str = "",
**kwargs: Any,
) -> str:
event = CallbackEvent(event_id=event_id, event_type=event_type, payload=payload)
if event.to_response() is not None:
self._aqueue.put_nowait(event)
def on_event_end(
self,
event_type: CBEventType,
payload: Optional[Dict[str, Any]] = None,
event_id: str = "",
**kwargs: Any,
) -> None:
event = CallbackEvent(event_id=event_id, event_type=event_type, payload=payload)
if event.to_response() is not None:
self._aqueue.put_nowait(event)
def start_trace(self, trace_id: Optional[str] = None) -> None:
"""No-op."""
def end_trace(
self,
trace_id: Optional[str] = None,
trace_map: Optional[Dict[str, List[str]]] = None,
) -> None:
"""No-op."""
async def async_event_gen(self) -> AsyncGenerator[CallbackEvent, None]:
while not self._aqueue.empty() or not self.is_done:
try:
yield await asyncio.wait_for(self._aqueue.get(), timeout=0.1)
except asyncio.TimeoutError:
pass
@@ -1,253 +0,0 @@
import logging
import os
from typing import Any, Dict, List, Literal, Optional, Set
from llama_index.core.llms import ChatMessage, MessageRole
from llama_index.core.schema import NodeWithScore
from pydantic import BaseModel, Field, validator, field_validator
from pydantic.alias_generators import to_camel
logger = logging.getLogger("uvicorn")
class FileContent(BaseModel):
type: Literal["text", "ref"]
# If the file is pure text then the value is be a string
# otherwise, it's a list of document IDs
value: str | List[str]
class File(BaseModel):
id: str
content: FileContent
filename: str
filesize: int
filetype: str
class AnnotationFileData(BaseModel):
files: List[File] = Field(
default=[],
description="List of files",
)
class Config:
json_schema_extra = {
"example": {
"csvFiles": [
{
"content": "Name, Age\nAlice, 25\nBob, 30",
"filename": "example.csv",
"filesize": 123,
"id": "123",
"type": "text/csv",
}
]
}
}
alias_generator = to_camel
class Annotation(BaseModel):
type: str
data: AnnotationFileData | List[str]
def to_content(self) -> str | None:
if self.type == "document_file":
# We only support generating context content for CSV files for now
csv_files = [file for file in self.data.files if file.filetype == "csv"]
if len(csv_files) > 0:
return "Use data from following CSV raw content\n" + "\n".join(
[f"```csv\n{csv_file.content.value}\n```" for csv_file in csv_files]
)
else:
logger.warning(
f"The annotation {self.type} is not supported for generating context content"
)
return None
class Message(BaseModel):
role: MessageRole
content: str
annotations: List[Annotation] | None = None
class ChatData(BaseModel):
messages: List[Message]
data: Any = None
class Config:
json_schema_extra = {
"example": {
"messages": [
{
"role": "user",
"content": "What standards for letters exist?",
}
]
}
}
@field_validator("messages")
def messages_must_not_be_empty(cls, v):
if len(v) == 0:
raise ValueError("Messages must not be empty")
return v
def get_last_message_content(self) -> str:
"""
Get the content of the last message along with the data content if available.
Fallback to use data content from previous messages
"""
if len(self.messages) == 0:
raise ValueError("There is not any message in the chat")
last_message = self.messages[-1]
message_content = last_message.content
for message in reversed(self.messages):
if message.role == MessageRole.USER and message.annotations is not None:
annotation_contents = filter(
None,
[annotation.to_content() for annotation in message.annotations],
)
if not annotation_contents:
continue
annotation_text = "\n".join(annotation_contents)
message_content = f"{message_content}\n{annotation_text}"
break
return message_content
def get_history_messages(self) -> List[ChatMessage]:
"""
Get the history messages
"""
return [
ChatMessage(role=message.role, content=message.content)
for message in self.messages[:-1]
]
def is_last_message_from_user(self) -> bool:
return self.messages[-1].role == MessageRole.USER
def get_chat_document_ids(self) -> List[str]:
"""
Get the document IDs from the chat messages
"""
document_ids: List[str] = []
for message in self.messages:
if message.role == MessageRole.USER and message.annotations is not None:
for annotation in message.annotations:
if (
annotation.type == "document_file"
and annotation.data.files is not None
):
for fi in annotation.data.files:
if fi.content.type == "ref":
document_ids += fi.content.value
return list(set(document_ids))
class LlamaCloudFile(BaseModel):
file_name: str
pipeline_id: str
def __eq__(self, other):
if not isinstance(other, LlamaCloudFile):
return NotImplemented
return (
self.file_name == other.file_name and self.pipeline_id == other.pipeline_id
)
def __hash__(self):
return hash((self.file_name, self.pipeline_id))
class SourceNodes(BaseModel):
id: str
metadata: Dict[str, Any]
score: Optional[float]
text: str
url: Optional[str]
@classmethod
def from_source_node(cls, source_node: NodeWithScore):
metadata = source_node.node.metadata
url = cls.get_url_from_metadata(metadata)
#text = 'filename' in metadata and metadata['filename'] or source_node.node.node_id
text = source_node.node.text
return cls(
id=source_node.node.node_id,
metadata=metadata,
score=source_node.score,
text=text, # type: ignore
url=url,
)
@classmethod
def get_url_from_metadata(cls, metadata: Dict[str, Any]) -> str:
url_prefix = os.getenv("FILESERVER_URL_PREFIX")
if not url_prefix:
logger.warning(
"Warning: FILESERVER_URL_PREFIX not set in environment variables. Can't use file server"
)
file_name = metadata.get("file_name")
if file_name and url_prefix:
# file_name exists and file server is configured
pipeline_id = metadata.get("pipeline_id")
if pipeline_id and metadata.get("private") is None:
# file is from LlamaCloud and was not ingested locally
file_name = f"{pipeline_id}${file_name}"
return f"{url_prefix}/output/llamacloud/{file_name}"
is_private = metadata.get("private", "false") == "true"
if is_private:
return f"{url_prefix}/output/uploaded/{file_name}"
return f"{url_prefix}/data/{file_name}"
else:
# fallback to URL in metadata (e.g. for websites)
return metadata.get("URL")
@classmethod
def from_source_nodes(cls, source_nodes: List[NodeWithScore]):
return [cls.from_source_node(node) for node in source_nodes]
@staticmethod
def get_download_files(nodes: List[NodeWithScore]) -> Set[LlamaCloudFile]:
source_nodes = SourceNodes.from_source_nodes(nodes)
llama_cloud_files = [
LlamaCloudFile(
file_name=node.metadata.get("file_name"),
pipeline_id=node.metadata.get("pipeline_id"),
)
for node in source_nodes
if (
node.metadata.get("private")
is None # Only download files are from LlamaCloud and were not ingested locally
and node.metadata.get("pipeline_id") is not None
and node.metadata.get("file_name") is not None
)
]
# Remove duplicates and return
return set(llama_cloud_files)
class Result(BaseModel):
result: Message
nodes: List[SourceNodes]
class ChatConfig(BaseModel):
starter_questions: Optional[List[str]] = Field(
default=None,
description="List of starter questions",
serialization_alias="starterQuestions",
)
class Config:
json_schema_extra = {
"example": {
"starterQuestions": [
"What standards for letters exist?",
"What are the requirements for a letter to be considered a letter?",
]
}
}
@@ -1,25 +0,0 @@
import logging
from typing import List
from fastapi import APIRouter, HTTPException
from pydantic import BaseModel
from app.api.services.file import PrivateFileService
file_upload_router = r = APIRouter()
logger = logging.getLogger("uvicorn")
class FileUploadRequest(BaseModel):
base64: str
@r.post("")
def upload_file(request: FileUploadRequest) -> List[str]:
try:
logger.info("Processing file")
return PrivateFileService.process_file(request.base64)
except Exception as e:
logger.error(f"Error processing file: {e}", exc_info=True)
raise HTTPException(status_code=500, detail="Error processing file")
@@ -1,109 +0,0 @@
import json
from aiostream import stream
from fastapi import Request
from fastapi.responses import StreamingResponse
from llama_index.core.chat_engine.types import StreamingAgentChatResponse
from app.api.routers.events import EventCallbackHandler
from app.api.routers.models import ChatData, Message, SourceNodes
from app.api.services.suggestion import NextQuestionSuggestion
class VercelStreamResponse(StreamingResponse):
"""
Class to convert the response from the chat engine to the streaming format expected by Vercel
"""
TEXT_PREFIX = "0:"
DATA_PREFIX = "8:"
@classmethod
def convert_text(cls, token: str):
# Escape newlines and double quotes to avoid breaking the stream
token = json.dumps(token)
return f"{cls.TEXT_PREFIX}{token}\n"
@classmethod
def convert_data(cls, data: dict):
data_str = json.dumps(data)
return f"{cls.DATA_PREFIX}[{data_str}]\n"
def __init__(
self,
request: Request,
event_handler: EventCallbackHandler,
response: StreamingAgentChatResponse,
chat_data: ChatData,
):
content = VercelStreamResponse.content_generator(
request, event_handler, response, chat_data
)
super().__init__(content=content)
@classmethod
async def content_generator(
cls,
request: Request,
event_handler: EventCallbackHandler,
response: StreamingAgentChatResponse,
chat_data: ChatData,
):
# Yield the text response
async def _chat_response_generator():
final_response = ""
async for token in response.async_response_gen():
final_response += token
yield VercelStreamResponse.convert_text(token)
# Generate questions that user might interested to
conversation = chat_data.messages + [
Message(role="assistant", content=final_response)
]
questions = await NextQuestionSuggestion.suggest_next_questions(
conversation
)
if len(questions) > 0:
yield VercelStreamResponse.convert_data(
{
"type": "suggested_questions",
"data": questions,
}
)
# the text_generator is the leading stream, once it's finished, also finish the event stream
event_handler.is_done = True
# Yield the source nodes
yield cls.convert_data(
{
"type": "sources",
"data": {
"nodes": [
SourceNodes.from_source_node(node).dict()
for node in response.source_nodes
]
},
}
)
# Yield the events from the event handler
async def _event_generator():
async for event in event_handler.async_event_gen():
event_response = event.to_response()
if event_response is not None:
yield VercelStreamResponse.convert_data(event_response)
combine = stream.merge(_chat_response_generator(), _event_generator())
is_stream_started = False
async with combine.stream() as streamer:
async for output in streamer:
if not is_stream_started:
is_stream_started = True
# Stream a blank message to start the stream
yield VercelStreamResponse.convert_text("")
yield output
if await request.is_disconnected():
break
+616
View File
@@ -0,0 +1,616 @@
import asyncio
import json
import logging
import time
from typing import Dict, List, Any, Optional, AsyncGenerator
from aiostream import stream
from fastapi import APIRouter, Request,HTTPException
from fastapi.responses import StreamingResponse
from llama_index.core import BaseCallbackHandler
from llama_index.core.base.llms.types import ChatMessage
from llama_index.core.callbacks import CBEventType
from llama_index.core.chat_engine.types import StreamingAgentChatResponse
from llama_index.core.tools import ToolOutput
from llama_index.core.schema import NodeWithScore
from pydantic import BaseModel
from app.api.routers.request.base import userMng, conversations,message,ProjectInfo,feedback
from app.api.routers.request.baseConfig import *
from app.api.routers.request.models import ChatRequestData,ChatFileUploadRequest
from app.engine import get_chat_engine
import uuid
from app.api.routers.services.fileServices import PrjFileLoadService,ChatFileService
from app.api.routers.services.suggestion import NextQuestionSuggestion
import time
from llama_index.core.settings import Settings
logger = logging.getLogger("uvicorn")
v1_router = v = APIRouter()
gEvent_handler = None
CH_Event_map={
'CHUNKING':'文本切片',
'NODE_PARSING':'节点解析',
'EMBEDDING':'生成向量',
'LLM':'知识问答',
'QUERY':'查询',
'RETRIEVE':'检索',
'SYNTHESIZE':'答案合成',
'TREE':'总结',
'SUB_QUESTION':'问题分解',
'TEMPLATING':'生成提示词模板',
'FUNCTION_CALL':'函数调用',
'RERANKING':'节点重排',
'EXCEPTION':'执行异常',
'AGENT_STEP':'单步执行'
}
class ChatCallbackEvent(BaseModel):
event_type: ChatEventType
payload: Optional[Dict[str, Any]] = None
def get_common_param(self)-> dict:
return {
'event': self.event_type.value,
'conversation_id':self.payload.get("conversation_id"),
'message_id': self.payload.get("message_id"),
'created_at': int(time.time()),
'task_id': self.payload.get("task_id")
}
def get_WorkflowStart_param(self) -> dict:
params = self.get_common_param()
params.update({
'workflow_run_id':self.payload.get('workflow_run_id'),
'data':{
"id": self.payload.get('workflow_run_id'),
"workflow_id": self.payload.get('workflow_id'),
"sequence_number": 1709,
"inputs": {
"sys.query": f"开始查询 {self.payload.get('query')}",
"sys.files": [],
"sys.conversation_id": self.payload.get('conversation_id'),
"sys.user_id": self.payload.get('use_id')
},
"created_at": int(time.time())
}
})
return params
def get_WorkflowFinished_param(self) -> dict:
params = self.get_common_param()
params.update({
'workflow_run_id':self.payload.get('workflow_run_id'),
'data':{
"id": self.payload.get('workflow_run_id'),
"workflow_id": self.payload.get('workflow_id'),
"sequence_number": 1709,
"status": "succeeded",
"outputs": {
"answer": self.payload.get('response')
},
"error": '',
"elapsed_time": 36.03764106379822,
"total_tokens": 11707,
"total_steps": 10,
"created_by": {
"id": str(uuid.uuid4()),
"user": self.payload.get('use_id')
},
"created_at": int(time.time()),
"finished_at": int(time.time()),
"files": []
}
})
return params
def get_NodeStart_param(self) -> dict:
params = self.get_common_param()
params.update({
'workflow_run_id':self.payload.get('workflow_run_id'),
'data':{
"id": self.payload.get('nodeid'),
"node_id": self.payload.get('nodeid'),
"node_type": "http-request",
"title": CH_Event_map[self.payload.get('title')],
"index": self.payload.get('index'),
"predecessor_node_id": self.payload.get('predecessor_node_id'),
"inputs": '',
"created_at": 1724398751,
"extras": {}
}
})
return params
def get_NodeFinished_param(self) -> dict:
params = self.get_common_param()
params.update({
'workflow_run_id':self.payload.get('workflow_run_id'),
'data':{
"id": self.payload.get('nodeid'),
"node_id": self.payload.get('nodeid'),
"node_type": "http-request",
"title": CH_Event_map[self.payload.get('title')],
"index": self.payload.get('index'),
"predecessor_node_id": self.payload.get('predecessor_node_id'),
"inputs": '',
"process_data": '',
"outputs": '',
"status": "succeeded",
"error": '',
"elapsed_time": 0.10402441816404462,
"execution_metadata": '',
"created_at": 1724398751,
"finished_at": 1724398751,
"files": []
}
})
return params
def get_Message_param(self) -> dict:
params = self.get_common_param()
params.update({
'id':self.payload.get('message_id'),
'answer':self.payload.get('answer')
})
return params
def get_MessageEnd_param(self) -> dict:
params = self.get_common_param()
nodeInfos = []
source_nodes = self.payload.get('source_node')
if source_nodes is not None:
for i in range(len(source_nodes)):
source_node:NodeWithScore = source_nodes[i]
metadata:dict = source_node.node.metadata
nodeInfo = {
"position": i,
"dataset_id": metadata.get("pipeline_id"),
"dataset_name": metadata.get("file_name"),
"document_id": source_node.node_id,
"document_name": metadata.get("file_name"),
"data_source_type": "upload_file",
"segment_id": source_node.node_id,
"retriever_from": "workflow",
"score": source_node.score,
"hit_count": 1,
"word_count": 632,
"segment_position": i,
"index_node_hash": "",
"content": source_node.text
}
nodeInfos.append(nodeInfo)
params.update({
'id':self.payload.get('message_id'),
'metadata':{
"retriever_resources":nodeInfos,
"usage":{
"prompt_tokens": 4972,
"prompt_unit_price": "0.0",
"prompt_price_unit": "0.0",
"prompt_price": "0.0",
"completion_tokens": 332,
"completion_unit_price": "0.0",
"completion_price_unit": "0.0",
"completion_price": "0.0",
"total_tokens": 5304,
"total_price": "0.0",
"currency": "USD",
"latency": 4.897703120019287
}
}
})
return params
def to_response(self)-> dict|None:
try:
match self.event_type.value:
case "workflow_started":
return self.get_WorkflowStart_param()
case "workflow_finished":
return self.get_WorkflowFinished_param()
case "node_started":
return self.get_NodeStart_param()
case 'node_finished':
return self.get_NodeFinished_param()
case 'message':
return self.get_Message_param()
case 'message_end':
return self.get_MessageEnd_param()
case _:
return None
except Exception as e:
logger.error(f"转换回应时间时发生错误,原因: {e}")
return None
class ChatEventCallbackHandler(BaseCallbackHandler):
_aqueue: asyncio.Queue
is_done: bool = False
def __init__(self):
"""Initialize the base callback handler."""
ignored_events = [
# CBEventType.CHUNKING,
# CBEventType.NODE_PARSING,
# CBEventType.EMBEDDING,
# CBEventType.LLM,
# CBEventType.TEMPLATING,
]
super().__init__(ignored_events, ignored_events)
self._aqueue = asyncio.Queue()
self._response: StreamingAgentChatResponse = None
self._ids:Dict[str,Any] = {}
self._chatData:ChatRequestData = None
self._nodeStack:List[str] = []
self._firstEventID:str = None
def setInitParams(self,ids:dict,data:ChatRequestData):
self._ids = ids
self._chatData = data
self._firstEventID = None
def setResponse(self,response: StreamingAgentChatResponse):
self._response = response
def on_event_start(
self,
event_type: CBEventType,
payload: Optional[Dict[str, Any]] = None,
event_id: str = "",
**kwargs: Any,
) -> str:
if self._firstEventID is None:
self._firstEventID = event_id
self.start()
logger.info("event_start:{} type:{} payload:{}\n".format(event_id, event_type, payload))
self._nodeStack.append(event_id)
nindex = len(self._nodeStack) - 1
args:Dict[str,Any] = self._ids
args.update(
{
'nodeid':event_id,
'title':event_type.name,
'index':nindex + 1,
'predecessor_node_id': self._nodeStack[nindex - 1] if nindex > 0 else ''
}
)
nd_event = ChatCallbackEvent(event_type = ChatEventType.NODE_START,payload = args)
if nd_event.to_response() is not None:
self._aqueue.put_nowait(nd_event)
def on_event_end(
self,
event_type: CBEventType,
payload: Optional[Dict[str, Any]] = None,
event_id: str = "",
**kwargs: Any,
) -> None:
logger.info("event_end:{} type:{} payload:{}\n".format(event_id, event_type, payload))
#self.response = payload.get("response","")
args:Dict[str,Any] = self._ids
nodeID = self._nodeStack[-1]
if nodeID == event_id:
nindex = len(self._nodeStack) - 1
args.update(
{
'nodeid':event_id,
'title':event_type.name,
'index':nindex + 1,
'predecessor_node_id':self._nodeStack[nindex - 1] if nindex > 0 else ''
}
)
nd_event = ChatCallbackEvent(event_type = ChatEventType.NODE_FINISHED,payload = args)
if nd_event.to_response() is not None:
self._aqueue.put_nowait(nd_event)
self._nodeStack.pop()
if self._firstEventID is not None and self._firstEventID == event_id:
self.finished()
def start_trace(self, trace_id: Optional[str] = None) -> None:
"""No-op."""
logger.info("trace_start:{}\n".format(trace_id))
def end_trace(
self,
trace_id: Optional[str] = None,
trace_map: Optional[Dict[str, List[str]]] = None,
) -> None:
"""No-op."""
logger.info("trace_end:{} trace_map:{}\n".format(trace_id, trace_map))
async def async_event_gen(self) -> AsyncGenerator[ChatCallbackEvent, None]:
while not self._aqueue.empty() or not self.is_done:
try:
yield await asyncio.wait_for(self._aqueue.get(), timeout=0.1)
except asyncio.TimeoutError:
pass
def makeWorkflow_startEvent(self)->ChatCallbackEvent:
args:Dict[str,Any] = self._ids
args.update(
{
'use_id': self._chatData.user,
'query': self._chatData.query,
'conversation_id': self._chatData.conversation_id
}
)
return ChatCallbackEvent(event_type = ChatEventType.WORKFLOW_START,payload = args)
def makeWorkflow_finishedEvent(self)->ChatCallbackEvent:
args:Dict[str,Any] = self._ids
args.update(
{
'response': '',
'conversation_id': self._chatData.conversation_id
}
)
return ChatCallbackEvent(event_type = ChatEventType.WORKFLOW_FINISHED,payload = args)
def makeMessage_EndEvent(self)->ChatCallbackEvent:
args:Dict[str,Any] = self._ids
if self._response is not None:
args.update({
'source_node': self._response.source_nodes
})
msgEnt_event = ChatCallbackEvent(event_type = ChatEventType.MESSAGE_END,payload = args)
return msgEnt_event
def start(self):
#添加工作流开始事件
wf_event = self.makeWorkflow_startEvent()
if wf_event.to_response() is not None:
self._aqueue.put_nowait(wf_event)
def finished(self):
wf_event = self.makeWorkflow_finishedEvent()
if wf_event.to_response() is not None:
self._aqueue.put_nowait(wf_event)
msgEnt_event = self.makeMessage_EndEvent()
if msgEnt_event.to_response() is not None:
self._aqueue.put_nowait(msgEnt_event)
class IDManager:
def createID(self):
return {
"message_id" : str(uuid.uuid4()),
'task_id':str(uuid.uuid4()),
'workflow_run_id': str(uuid.uuid4()),
"workflow_id": str(uuid.uuid4())
}
class ChatStreamResponse(StreamingResponse):
TEXT_PREFIX = "data: "
DATA_PREFIX = "data: "
ids:Dict[str,Any] = {}
data:ChatRequestData = None
@classmethod
def convert_Message(cls, token: str):
params = cls.ids
params.update({
'answer':token,
'conversation_id':cls.data.conversation_id
})
event = ChatCallbackEvent(event_type = ChatEventType.MESSAGE,payload = params)
data_str = json.dumps(event.to_response())
return f"{cls.DATA_PREFIX}{data_str}\n\n"
@classmethod
def convert_Event(cls, data: dict):
data_str = json.dumps(data)
return f"{cls.DATA_PREFIX}{data_str}\n\n"
def __init__(
self,
request: Request,
event_handler: ChatEventCallbackHandler,
response: StreamingAgentChatResponse,
data: ChatRequestData,
ids:Dict[str,Any]
):
ChatStreamResponse.ids = ids
ChatStreamResponse.data = data
content = ChatStreamResponse.content_generator(
request, event_handler, response, data
)
super().__init__(content=content)
@classmethod
async def content_generator(
cls,
request: Request,
event_handler: ChatEventCallbackHandler,
response: StreamingAgentChatResponse,
data: ChatRequestData
):
# Yield the text response
async def _chat_response_generator():
final_response = ""
async for token in response.async_response_gen():
final_response += token
yield ChatStreamResponse.convert_Message(token)
# 存储消息历史
message().add(user_id=data.user,conversation_id=data.conversation_id,query=data.query,answer=final_response)
# the text_generator is the leading stream, once it's finished, also finish the event stream
event_handler.is_done = True
event_handler.setResponse(response)
# Yield the events from the event handler
async def _event_generator():
async for event in event_handler.async_event_gen():
event_response = event.to_response()
if event_response is not None:
yield ChatStreamResponse.convert_Event(event_response)
combine = stream.merge(_chat_response_generator(), _event_generator())
is_stream_started = False
async with combine.stream() as streamer:
async for output in streamer:
if not is_stream_started:
is_stream_started = True
yield output
if await request.is_disconnected():
break
@v.post("/chat-messages")
async def post_chatmessages(request: Request, data: ChatRequestData):
global gEvent_handler
userMng.findNoExistCreate(data.user)
data.conversation_id = data.conversation_id if data.conversation_id else str(uuid.uuid4())
conversaObj = conversations()
conversationinfo = conversaObj.get(data.conversation_id)
if conversationinfo is None:
conversationinfo = conversaObj.add(data.conversation_id, data.user, "新建会话",inputs= data.inputs)
# 生成聊天参数
last_message_content = ChatMessage.from_str(data.query)
filters = None
params = data.inputs or {}
# 启动聊天事件监听
ids = IDManager().createID()
if gEvent_handler is None:
gEvent_handler = ChatEventCallbackHandler()
Settings.llm.callback_manager.handlers.append(gEvent_handler)
if gEvent_handler is not None:
gEvent_handler.setInitParams(ids = ids,data = data)
# 获取聊天引擎对象
chat_engine = get_chat_engine(filters=filters, params=params)
# 执行异步聊天
response = await chat_engine.astream_chat(data.query)
# 返回异步消息回应
return ChatStreamResponse(request, gEvent_handler, response, data,ids)
@v.get("/messages")
async def query_messages(user:str, conversation_id:str):
#conversation_id = default_conversation_id if conversation_id is None else conversation_id
datas = []
records = message().gets(user,conversation_id)
if records is None:
return {
"limit": 20,
"has_more": False,
"data": []
}
for record in records:
res = record.dict()
feeds = feedback().query(res['id'])
res["message_files"] = []
res["feedback"] = {'rating':feeds['rating'] } if feeds != None else ''
res["retriever_resources"] = []
res["created_at"] = 1723444905
res["agent_thoughts"] = []
res["status"] = "normal"
res["error"] = ''
datas.append(res)
return {
"limit": 20,
"has_more": False,
"data": datas
}
@v.post("/conversations/{itemid}/name")
async def post_conversations(request: Request,itemid:str,params:Dict[str,Any]):
consaObj = conversations()
consaObj.rename(itemid,'知识问答')
cond = {
'id':itemid,
'user_id':params['user']
}
results = consaObj.query(**cond)
if len(results) > 0:
res = results[0]
return {
"id": res['id'],
"name": res['name'],
"inputs": res['inputs'],
"status": res['status'],
"introduction": res['introduction'],
"created_at": res['created_at'],
#"工程位置"
}
return 'null'
@v.get("/conversations")
async def query_conversations(user:str, first_id:str = None, limit:str = None, pinned:str = None):
user_id = '' if user is None else user
userMng.findNoExistCreate(user_id)
return {
"limit": 20,
"has_more": False,
"data": conversations().gets(user_id)
}
@v.get("/parameters")
async def query_parameters(user:str):
prjObj = ProjectInfo()
return BaseConfig().ParamterCfg(projectInfo = prjObj.projectNames())
@v.post("/messages/{message_id}/feedbacks")
async def post_feedbacks(request: Request,message_id:str,params:Dict[str,Any]):
if params['rating'] is None:
feedback().delete(message_id)
else:
results = message().query(message_id)
if len(results) > 0:
result = results[0]
feedback().add(message_id=message_id,query=result['query'],
answer=result['answer'],rating=params['rating'])
@v.post("/files/upload")
def upload_file(request: ChatFileUploadRequest):
try:
logger.info("Processing file")
resluts = ChatFileService.process_file(request.base64)
return {
'id':resluts.get('id'),
'name': resluts.get('name'),
'size': resluts.get('size'),
'extension':resluts.get('extension'),
'mime_type':resluts.get('mime_type'),
'created_by':str(uuid.uuid4()),
'created_at':int(time.time())
}
except Exception as e:
logger.error(f"Error processing file: {e}", exc_info=True)
raise HTTPException(status_code=500, detail="Error processing file")
@v.post("/project")
def upload_file(request: ChatFileUploadRequest):
try:
logger.info("Processing file")
return PrjFileLoadService.process_file(request.base64)
except Exception as e:
logger.error(f"Error processing file: {e}", exc_info=True)
raise HTTPException(status_code=500, detail="Error processing file")
@v.post("/messages/{message_id}/suggested")
async def post_suggested(request: Request,message_id:str,user:str):
questions = await NextQuestionSuggestion.suggest_next_questions(message_id)
return {
"result": "success",
"data":questions
}
+189
View File
@@ -0,0 +1,189 @@
from datetime import datetime
import uuid
from app.api.routers.request.baseConfig import BaseConfig
from app.api.routers.request.dbOrm import DBManager
from typing import List
dbManage = DBManager()
class conversations:
def __init__(self) -> None:
self._tableName = 'conversations'
dbManage.createTable(self._tableName)
def gets(self,user_id:str):
records = dbManage.query(self._tableName,user_id = user_id)
datas = []
for record in records:
datas.append(record)
return datas
def get(self, id:str):
records = dbManage.query(self._tableName, id=id)
if len(records) >0:
return records[0]
return None
def add(self,id:str, user_id:str, name:str,inputs:dict):
template = BaseConfig().ConversationCfg()
template['id'] = id
template['user_id'] = user_id
template['name'] = name
template['created_at'] = 1724399038
template['inputs'] = inputs
dbManage.addRecord(self._tableName,template)
def delete(self,id:str):
dbManage.delete(self._tableName,id=id)
def rename(self,id:str,name:str):
data = {'name':name}
dbManage.update(self._tableName,data,id=id)
def query(self,**condition):
results = []
records = dbManage.query(self._tableName,**condition)
for record in records:
results.append(record.dict())
return results
class user:
def __init__(self) -> None:
self._tableName = 'user'
dbManage.createTable(self._tableName)
def gets(self):
return dbManage.query(self._tableName)
def get(self,id:str):
return dbManage.query(self._tableName,id = id)
def add(self,id:str):
info = {
'id':id,
'createtime': datetime.now().strftime("%Y-%m-%d %H:%M:%S")
}
dbManage.addRecord(self._tableName,info)
def delete(self,id:str):
dbManage.delete(self._tableName,id = id)
class userMng:
userObj = user()
@classmethod
def findNoExistCreate(cls,user_id:str):
userInfo = cls.userObj.get(user_id)
if len(userInfo) == 0:
cls.userObj.add(user_id)
def remove(cls,user_id:str):
cls.userObj.delete(user_id)
class parameter:
def __init__(self) -> None:
self._tableName = 'parameters'
dbManage.createTable(self._tableName)
def get(self,user_id:str):
records = dbManage.query(self._tableName,user_id = user_id)
data = {}
for record in records:
key = record['name']
value = record['value']
data[key] = value
return data
def set(self,user_id:str):
dbManage.addRecord(self._tableName,{})
def delete(self,user_id:str):
dbManage.delete(self._tableName,user_id = user_id)
class message:
def __init__(self) -> None:
self._tableName = 'messages'
dbManage.createTable(self._tableName)
def gets(self,user_id:str,conversation_id:str):
records = dbManage.query(self._tableName,user_id = user_id,conversation_id = conversation_id)
datas = []
for record in records:
datas.append(record)
return datas
def add(self,user_id:str,conversation_id:str,query:str,answer:str):
template = BaseConfig.MessageCfg()
template['id'] = str(uuid.uuid4())
template['user_id'] = user_id
template['conversation_id'] = conversation_id
template['query'] = query
template['answer'] = answer
dbManage.addRecord(self._tableName,template)
def delete(self,user_id:str):
dbManage.delete(self._tableName,user_id = user_id)
def query(self,id:str):
results = []
condition = {'id':id}
records = dbManage.query(self._tableName,**condition)
for record in records:
results.append(record.dict())
return results
class feedback:
def __init__(self) -> None:
self._tableName = 'feedbacks'
dbManage.createTable(self._tableName)
def add(self,message_id:str,query:str,answer:str,rating:str):
record = {
'message_id': message_id,
'query': query,
'answer': answer,
'rating': rating,
}
dbManage.addRecord(self._tableName,record)
def delete(self,message_id:str):
cond = {'message_id':message_id}
dbManage.delete(self._tableName,**cond)
def query(self,message_id:str):
cond = {'message_id':message_id}
records = dbManage.query(self._tableName,**cond)
if len(records) > 0:
return records[0].dict()
return None
class ProjectInfo:
def __init__(self) -> None:
self._tableName = 'projectInfos'
dbManage.createTable(self._tableName)
def add(self,name:str,flag:str):
info = dbManage.query(self._tableName,prjFlag = flag)
if len(info) == 0:
record = {
'prjectName': name,
'prjFlag': flag
}
dbManage.addRecord(self._tableName,record)
def projectNames(self)->List[str]:
records = dbManage.query(self._tableName)
names = []
for record in records:
data:dict = record.dict()
name = data.get('prjectName')
if name !='':
names.append(name)
return names
def prjFalg(self,name:str):
records = dbManage.query(self._tableName)
for record in records:
data:dict = record.dict()
if data.get('prjectName') == name:
return data['prjFlag']
return ''
@@ -0,0 +1,103 @@
from pydantic import BaseModel
import os
from enum import Enum
class BaseConfig(BaseModel):
projectInfo:str = os.getenv("PROJECT_TITLE","会话提示消息")
def ParamterCfg(self,**args):
prjItems = args.get('projectInfo')
questions = os.getenv("CONVERSATION_STARTERS", "dev")
return{
"opening_statement": self.projectInfo,
"suggested_questions": questions.split('\n'),
"suggested_questions_after_answer": {
"enabled": False
},
"speech_to_text": {
"enabled": False
},
"text_to_speech": {
"enabled": False,
"language": "",
"voice": ""
},
"retriever_resource": {
"enabled": True
},
"annotation_reply": {
"enabled": False
},
"more_like_this": {
"enabled": False
},
"user_input_form": [
{
"select": {
"variable": "projectname",
"label": "\u5de5\u7a0b\u540d\u79f0",
"type": "select",
"max_length": 48,
"required": True,
"options": prjItems
}
}
],
"sensitive_word_avoidance": {
"enabled": False
},
"file_upload": {
"image": {
"enabled": False,
"number_limits": 3,
"transfer_methods": [
"remote_url"
]
}
},
"system_parameters": {
"image_file_size_limit": "10",
"language": "",
"voice": "",
},
"retriever_resource": {
"enabled": True
},
"annotation_reply": {
"enabled": False
},
"more_like_this": {
"enabled": False
},
}
def ConversationCfg(self):
return{
"id": "",
'user_id':'',
"name": "",
"inputs": {},
"status": "normal",
"introduction": self.projectInfo,
"created_at":''
}
@classmethod
def MessageCfg(cls):
return {
"id": "",
'user_id':'',
"conversation_id": "",
"inputs": {},
"query": "",
"answer": ""
}
class ChatEventType(str, Enum):
WORKFLOW_START = "workflow_started"
WORKFLOW_FINISHED = "workflow_finished"
NODE_START = "node_started"
NODE_FINISHED = "node_finished"
MESSAGE = "message"
MESSAGE_END = "message_end"
+239
View File
@@ -0,0 +1,239 @@
import os
from typing import Dict, List, Any
from pydantic import BaseModel
from sqlalchemy import create_engine, Column, String, Integer, JSON,Float
from sqlalchemy.engine.reflection import Inspector
from sqlalchemy.orm import sessionmaker, declarative_base
Base = declarative_base()
#orm类
class ConversationOrm(Base):
__tablename__ = "conversations"
id = Column(String, primary_key=True)
user_id = Column(String)
name = Column(String)
inputs = Column(JSON)
status = Column(String)
introduction = Column(String)
created_at = Column(Integer)
def update(self,data:Dict[str,Any]):
if 'name' in data:
self.name = data['name']
class UserOrm(Base):
__tablename__ = "user"
id = Column(String, primary_key=True)
createtime = Column(String)
class ParametersOrm(Base):
__tablename__ = "parameters"
user_id = Column(String,primary_key=True)
name = Column(String)
value = Column(JSON)
class MessagesOrm(Base):
__tablename__ = "messages"
id = Column(String,primary_key=True)
user_id = Column(String)
conversation_id = Column(String)
inputs = Column(JSON)
query = Column(String)
answer = Column(String)
class FeedBackOrm(Base):
__tablename__ = "feedbacks"
message_id = Column(String,primary_key=True)
query = Column(String)
answer = Column(String)
rating = Column(String)
class ProjectInfoOrm(Base):
__tablename__ = "projectInfos"
prjFlag = Column(String,primary_key=True)
prjectName = Column(String)
#数据结构
class ConversationModel(BaseModel):
id: str
name: str
inputs: Dict[str, Any]
status: str
introduction: str
created_at: int
class Config:
from_attributes=True
@classmethod
def orm(cls):
return ConversationOrm
class UserModel(BaseModel):
id: str
createtime: str
class Config:
from_attributes=True
@classmethod
def orm(cls):
return UserOrm
class ParametersModel(BaseModel):
user_id : str
name : str
value : Dict[str, Any]
class Config:
from_attributes=True
@classmethod
def orm(cls):
return ParametersOrm
class MessagesModel(BaseModel):
id :str
conversation_id :str
inputs : Dict[str, Any]
query : str
answer : str
class Config:
from_attributes=True
@classmethod
def orm(cls):
return MessagesOrm
class FeedBackModel(BaseModel):
message_id :str
query :str
answer :str
rating :str
class Config:
from_attributes=True
@classmethod
def orm(cls):
return FeedBackOrm
class ProjectInfoModel(BaseModel):
prjectName:str
prjFlag:str
class Config:
from_attributes=True
@classmethod
def orm(cls):
return ProjectInfoOrm
class DBManager:
def __init__(self) -> None:
DATABASE_URL = os.getenv("SQLITE_DATABASE_URL")
self._engine = create_engine(DATABASE_URL)
self.SessionLocal = sessionmaker(autocommit=False, autoflush=False, bind=self._engine)
def createTable(self,tableName:str):
if self._engine is None:
return
if not self.exist(tableName):
Base.metadata.tables[tableName].create(self._engine)
def addRecord(self,tableName:str,record:Dict[str,Any]):
ormCls = self._get_orm(tableName)
if ormCls is None:
return
session = self.SessionLocal()
data = ormCls(**record)
session.add(data)
session.commit()
def addRecords(self,tableName:str,records:List[Dict[str,Any]]):
ormCls = self._get_orm(tableName)
if ormCls is None:
return
datas = []
session = self.SessionLocal()
for record in records:
datas.append(ormCls(**record))
session.add(datas)
session.commit()
def delete(self,tableName:str,**filter):
session = self.SessionLocal()
ormCls = self._get_orm(tableName)
if ormCls is None:
return
records = session.query(ormCls).filter_by(**filter).all()
if records is not None:
for record in records:
session.delete(record)
session.commit()
def update(self,tableName:str,data:Dict[str,Any],**filter):
if not self.exist(tableName):
return
session = self.SessionLocal()
ormCls = self._get_orm(tableName)
if ormCls is None:
return
if len(filter) > 0:
records = session.query(ormCls).filter_by(**filter).all()
else:
records = session.query(ormCls).all()
for record in records:
if record is not None:
record.update(data)
session.commit()
def query(self,tableName:str,**filter):
session = self.SessionLocal()
ormCls = self._get_orm(tableName)
if ormCls is None:
return
modelCls = self._get_model(ormCls)
if modelCls is None:
return
if filter is not None:
records = session.query(ormCls).filter_by(**filter).all()
else:
records = session.query(ormCls).all()
datas = []
for record in records:
datas.append(modelCls.from_orm(record))
return datas
def exist(self,tableName:str)->bool:
if self._engine is None:
return
inspector = Inspector.from_engine(self._engine)
return inspector.has_table(tableName)
def _get_orm(self,tableName:str):
subClss = Base.__subclasses__()
for sunCls in subClss:
if sunCls.__tablename__ == tableName:
return sunCls
return None
def _get_model(self,orm:Any):
subClss = BaseModel.__subclasses__()
for sunCls in subClss:
if 'orm' in sunCls.__dict__ and sunCls.orm() == orm:
return sunCls
return None
+17
View File
@@ -0,0 +1,17 @@
from typing import Dict, Any
from pydantic import BaseModel
from typing import Optional
class ChatRequestData(BaseModel):
inputs: Dict[str,Any]
query: str
user: str
response_mode: str
files: Any
conversation_id: str = None
class ChatFileUploadRequest(BaseModel):
base64: str
@@ -0,0 +1,134 @@
import base64,os,mimetypes,requests,tempfile
from typing import List,Dict,Any
from uuid import uuid4
from app.settings import init_settings
from app.engine.loaders import get_document_Types, get_documents,getFileCacahePath
from app.engine.vectordb import get_vector_store
from app.engine.generate import get_doc_store,run_pipeline,persist_storage
from llama_index.core.schema import Document
from pathlib import Path
from llama_index.core.readers.file.base import (
_try_loading_included_file_formats as get_file_loaders_map,
)
from llama_index.readers.file import FlatReader
from llama_index.core.ingestion import IngestionPipeline
from llama_index.core import VectorStoreIndex
from app.engine.index import get_index
STORAGE_DIR = os.getenv("STORAGE_DIR", "storage")
class PrjFileLoadService:
@staticmethod
def store_and_parse_file(file_data):
prjtoJson_url = os.getenv('PRJTOJSON_URL')
convert_url = prjtoJson_url +'/prj_convert_clt2json'
files ={'file':file_data}
response1 = requests.post(
url = convert_url,
files=files
)
if response1.text is None or response1.text=='':
return None
load_url = prjtoJson_url +'/file_download'
response2 = requests.post(
url = load_url,
data=response1.text
)
if response2.text is None or response2.content=='':
return None
try:
tempFilePath:str = tempfile.gettempdir() + f"\\{uuid4().hex}.zip"
with open(tempFilePath,'wb') as file:
file.write(response2.content)
prjID = str(uuid4())
filePath = getFileCacahePath() + f'/Projects/{prjID}'
os.makedirs(filePath)
import zipfile
with zipfile.ZipFile(tempFilePath,'r') as zip_File:
for zip_info in zip_File.infolist():
zip_info.filename = zip_info.filename.encode('cp437').decode('gbk')
zip_File.extract(zip_info,filePath)
os.remove(tempFilePath)
return f'Projects_{prjID}'
except Exception as e:
return None
@staticmethod
def process_file(base64_content: str) -> str:
prjFlag = PrjFileLoadService.store_and_parse_file(base64_content)
if prjFlag is None:
return None
#生成向量并持久化至本地
documents = get_documents(prjFlag)
for doc in documents:
doc.metadata["private"] = "false"
docstore = get_doc_store(prjFlag)
vector_store = get_vector_store(prjFlag)
_ = run_pipeline(docstore, vector_store, documents)
persist_storage(docstore, vector_store)
return prjFlag
class ChatFileService:
PRIVATE_STORE_PATH = os.getenv('CHAT_UPLOAD_FILECACHE','output/uploaded')
resluts:Dict[str,Any] = {}
@staticmethod
def process_file(base64_content: str) -> dict:
file_data, extension = ChatFileService.preprocess_base64_file(base64_content)
documents = ChatFileService.store_and_parse_file(file_data, extension)
pipeline = IngestionPipeline()
nodes = pipeline.run(documents=documents)
current_index = get_index()
pipeline = IngestionPipeline()
nodes = pipeline.run(documents=documents)
if current_index is None:
current_index = VectorStoreIndex(nodes=nodes)
else:
current_index.insert_nodes(nodes=nodes)
current_index.storage_context.persist(
persist_dir=os.environ.get("STORAGE_DIR", "storage")
)
return ChatFileService.resluts
@staticmethod
def preprocess_base64_file(base64_content: str) -> tuple:
header, data = base64_content.split(",", 1)
mime_type = header.split(";")[0].split(":", 1)[1]
extension = mimetypes.guess_extension(mime_type)
ChatFileService.resluts['mime_type'] = mime_type
ChatFileService.resluts['extension'] = extension
return base64.b64decode(data), extension
@staticmethod
def store_and_parse_file(file_data, extension) -> List[Document]:
os.makedirs(ChatFileService.PRIVATE_STORE_PATH, exist_ok=True)
fileID = uuid4().hex
file_name = f"{fileID}{extension}"
file_path = Path(os.path.join(ChatFileService.PRIVATE_STORE_PATH, file_name))
ChatFileService.resluts['id'] = fileID
ChatFileService.resluts['file_name'] = file_name
with open(file_path, "wb") as f:
f.write(file_data)
ChatFileService.resluts['size'] = os.path.getsize(file_path)
reader_cls = ChatFileService.default_file_loaders_map().get(extension)
if reader_cls is None:
raise ValueError(f"File extension {extension} is not supported")
reader = reader_cls()
documents = reader.load_data(file_path)
for doc in documents:
doc.metadata["file_name"] = file_name
doc.metadata["private"] = "true"
return documents
@staticmethod
def default_file_loaders_map():
default_loaders = get_file_loaders_map()
default_loaders[".txt"] = FlatReader
return default_loaders
@@ -1,6 +1,6 @@
from typing import List
from app.api.routers.models import Message
from app.api.routers.request.base import message
from llama_index.core.prompts import PromptTemplate
from llama_index.core.settings import Settings
from pydantic import BaseModel
@@ -23,26 +23,21 @@ class NextQuestions(BaseModel):
class NextQuestionSuggestion:
@staticmethod
async def suggest_next_questions(
messages: List[Message],
message_id: str,
number_of_questions: int = N_QUESTION_TO_GENERATE,
) -> List[str]:
# Reduce the cost by only using the last two messages
last_user_message = None
last_assistant_message = None
for message in reversed(messages):
if message.role == "user":
last_user_message = f"User: {message.content}"
elif message.role == "assistant":
last_assistant_message = f"Assistant: {message.content}"
if last_user_message and last_assistant_message:
break
results = message().query(message_id)
if len(results) > 0:
last_user_message = results[0]['query']
last_assistant_message = results[0]['answer']
conversation: str = f"{last_user_message}\n{last_assistant_message}"
output: NextQuestions = await Settings.llm.astructured_predict(
NextQuestions,
prompt=NEXT_QUESTIONS_SUGGESTION_PROMPT,
conversation=conversation,
nun_questions=number_of_questions,
)
return output.questions
return []
@@ -1,113 +0,0 @@
import base64
import mimetypes
import os
from pathlib import Path
from typing import Dict, List
from uuid import uuid4
from app.engine.index import get_index
from llama_index.core import VectorStoreIndex
from llama_index.core.ingestion import IngestionPipeline
from llama_index.core.readers.file.base import (
_try_loading_included_file_formats as get_file_loaders_map,
)
from llama_index.core.readers.file.base import (
default_file_metadata_func,
)
from llama_index.core.schema import Document
from llama_index.indices.managed.llama_cloud.base import LlamaCloudIndex
from llama_index.readers.file import FlatReader
def get_llamaparse_parser():
from app.engine.loaders import load_configs
from app.engine.loaders.file import FileLoaderConfig, llama_parse_parser
config = load_configs()
file_loader_config = FileLoaderConfig(**config["file"])
if file_loader_config.use_llama_parse:
return llama_parse_parser()
else:
return None
def default_file_loaders_map():
default_loaders = get_file_loaders_map()
default_loaders[".txt"] = FlatReader
return default_loaders
class PrivateFileService:
PRIVATE_STORE_PATH = "output/uploaded"
@staticmethod
def preprocess_base64_file(base64_content: str) -> tuple:
header, data = base64_content.split(",", 1)
mime_type = header.split(";")[0].split(":", 1)[1]
extension = mimetypes.guess_extension(mime_type)
# File data as bytes
return base64.b64decode(data), extension
@staticmethod
def store_and_parse_file(file_data, extension) -> List[Document]:
# Store file to the private directory
os.makedirs(PrivateFileService.PRIVATE_STORE_PATH, exist_ok=True)
# random file name
file_name = f"{uuid4().hex}{extension}"
file_path = Path(os.path.join(PrivateFileService.PRIVATE_STORE_PATH, file_name))
# write file
with open(file_path, "wb") as f:
f.write(file_data)
# Load file to documents
# If LlamaParse is enabled, use it to parse the file
# Otherwise, use the default file loaders
reader = get_llamaparse_parser()
if reader is None:
reader_cls = default_file_loaders_map().get(extension)
if reader_cls is None:
raise ValueError(f"File extension {extension} is not supported")
reader = reader_cls()
documents = reader.load_data(file_path)
# Add custom metadata
for doc in documents:
doc.metadata["file_name"] = file_name
doc.metadata["private"] = "true"
return documents
@staticmethod
def process_file(base64_content: str) -> List[str]:
file_data, extension = PrivateFileService.preprocess_base64_file(base64_content)
documents = PrivateFileService.store_and_parse_file(file_data, extension)
# Only process nodes, no store the index
pipeline = IngestionPipeline()
nodes = pipeline.run(documents=documents)
# Add the nodes to the index and persist it
current_index = get_index()
# Insert the documents into the index
if isinstance(current_index, LlamaCloudIndex):
# LlamaCloudIndex is a managed index so we don't need to process the nodes
# just insert the documents
for doc in documents:
current_index.insert(doc)
else:
# Only process nodes, no store the index
pipeline = IngestionPipeline()
nodes = pipeline.run(documents=documents)
# Add the nodes to the index and persist it
if current_index is None:
current_index = VectorStoreIndex(nodes=nodes)
else:
current_index.insert_nodes(nodes=nodes)
current_index.storage_context.persist(
persist_dir=os.environ.get("STORAGE_DIR", "storage")
)
# Return the document ids
return [doc.doc_id for doc in documents]
@@ -1,114 +0,0 @@
import logging
import os
from typing import Any, Dict, List, Optional
import requests
from app.api.routers.models import LlamaCloudFile
logger = logging.getLogger("uvicorn")
class LLamaCloudFileService:
LLAMA_CLOUD_URL = "https://cloud.llamaindex.ai/api/v1"
LOCAL_STORE_PATH = "output/llamacloud"
DOWNLOAD_FILE_NAME_TPL = "{pipeline_id}${filename}"
@classmethod
def get_all_projects(cls) -> List[Dict[str, Any]]:
url = f"{cls.LLAMA_CLOUD_URL}/projects"
return cls._make_request(url)
@classmethod
def get_all_pipelines(cls) -> List[Dict[str, Any]]:
url = f"{cls.LLAMA_CLOUD_URL}/pipelines"
return cls._make_request(url)
@classmethod
def get_all_projects_with_pipelines(cls) -> List[Dict[str, Any]]:
try:
projects = cls.get_all_projects()
pipelines = cls.get_all_pipelines()
return [
{
**project,
"pipelines": [p for p in pipelines if p["project_id"] == project["id"]],
}
for project in projects
]
except Exception as error:
logger.error(f"Error listing projects and pipelines: {error}")
return []
@classmethod
def _get_files(cls, pipeline_id: str) -> List[Dict[str, Any]]:
url = f"{cls.LLAMA_CLOUD_URL}/pipelines/{pipeline_id}/files"
return cls._make_request(url)
@classmethod
def _get_file_detail(cls, project_id: str, file_id: str) -> Dict[str, Any]:
url = f"{cls.LLAMA_CLOUD_URL}/files/{file_id}/content?project_id={project_id}"
return cls._make_request(url)
@classmethod
def _download_file(cls, url: str, local_file_path: str):
logger.info(f"Downloading file to {local_file_path}")
# Create directory if it doesn't exist
os.makedirs(cls.LOCAL_STORE_PATH, exist_ok=True)
# Download the file
with requests.get(url, stream=True) as r:
r.raise_for_status()
with open(local_file_path, "wb") as f:
for chunk in r.iter_content(chunk_size=8192):
f.write(chunk)
logger.info("File downloaded successfully")
@classmethod
def download_llamacloud_pipeline_file(
cls,
file: LlamaCloudFile,
force_download: bool = False,
):
file_name = file.file_name
pipeline_id = file.pipeline_id
# Check is the file already exists
downloaded_file_path = cls.get_file_path(file_name, pipeline_id)
if os.path.exists(downloaded_file_path) and not force_download:
logger.debug(f"File {file_name} already exists in local storage")
return
try:
logger.info(f"Downloading file {file_name} for pipeline {pipeline_id}")
files = cls._get_files(pipeline_id)
if not files or not isinstance(files, list):
raise Exception("No files found in LlamaCloud")
for file_entry in files:
if file_entry["name"] == file_name:
file_id = file_entry["file_id"]
project_id = file_entry["project_id"]
file_detail = cls._get_file_detail(project_id, file_id)
cls._download_file(file_detail["url"], downloaded_file_path)
break
except Exception as error:
logger.info(f"Error fetching file from LlamaCloud: {error}")
@classmethod
def get_file_name(cls, name: str, pipeline_id: str) -> str:
return cls.DOWNLOAD_FILE_NAME_TPL.format(pipeline_id=pipeline_id, filename=name)
@classmethod
def get_file_path(cls, name: str, pipeline_id: str) -> str:
return os.path.join(cls.LOCAL_STORE_PATH, cls.get_file_name(name, pipeline_id))
@staticmethod
def _make_request(
url: str, data=None, headers: Optional[Dict] = None, method: str = "get"
):
if headers is None:
headers = {
"Accept": "application/json",
"Authorization": f'Bearer {os.getenv("LLAMA_CLOUD_API_KEY")}',
}
response = requests.request(method, url, headers=headers, data=data)
response.raise_for_status()
return response.json()
@@ -1,22 +0,0 @@
import logging
from llama_index.core.indices import VectorStoreIndex
from app.engine.vectordb import get_vector_store
logger = logging.getLogger("uvicorn")
index = None
def get_index(params=None):
global index
if index is None:
logger.info("Connecting vector store...")
store = get_vector_store()
# Load the index from the vector store
# If you are using a vector store that doesn't store text,
# you must load the index from both the vector store and the document store
index = VectorStoreIndex.from_vector_store(store)
logger.info("Finished load index from vector store.")
return index
@@ -1,61 +0,0 @@
import os
from llama_index.core.agent import AgentRunner, ReActChatFormatter
from llama_index.core.settings import Settings
from llama_index.core.tools.query_engine import QueryEngineTool
from app.engine.engine import create_query_engine, create_summary_query_engine
from app.engine.index import get_index
#from app.engine.loaders.db import makeDescriptionByEngine
from app.engine.tools import ToolFactory
def get_chat_engine(filters=None, params=None):
system_prompt = os.getenv("SYSTEM_PROMPT")
top_k = int(os.getenv("TOP_K", "3"))
use_reranker = os.getenv("RERANK_ENABLED")
tools = []
# 创建SQL查询工具
# sql_query_engine = create_summary_query_engine(index)
# sql_query_tool = QueryEngineTool.from_defaults(query_engine=sql_query_engine,
# name="zjdata_query_tool",
# description="来源于一个由博微公司电力造价软件编制的造价工程文件。该文件以多张表格的形式存储存储了整个工程的全部数据内容。适用于以详细的自然语言查询表格数据方式查询造价工程各项具体属性、费用的数值。请先使用“zj_query_tool”无法解决才使用本工具"
# )
#tools.append(sql_query_tool)
# Add query tool if index exists
index = get_index()
if index is not None:
summary_query_engine = create_summary_query_engine(index,top_k,use_reranker,filters)
summary_query_tool = QueryEngineTool.from_defaults( query_engine=summary_query_engine, name="summary_query_tool",
description="适用于任何需要进行全面总结、概括的要求。",
)
query_engine = create_query_engine(index,top_k,use_reranker,filters)
query_engine_tool = QueryEngineTool.from_defaults(query_engine=query_engine, name="zj_query_tool",
description="由博微公司编制的关于电力造价知识、电力造价编制软件知识和造价工程文件结构的知识库。适用于查询电力领域、电力造价领域、博微、博微电力、博微造价等业务等内容。如果本知识库没有直接答案但有解决思路的可以返回解决办法后建议使用“zjdata_query_tool”工具。",
)
tools.append(summary_query_tool)
tools.append(query_engine_tool)
# Add additional tools
tools += ToolFactory.from_env()
prefix_messages = ("""您的设计旨在帮助完成各种任务,从回答问题到提供其他类型分析的摘要。\n\n##工具\n\n你可以访问各种工具。你有责任按照你认为合适的顺序使用这些工具来完成当前的任务。\n这可能需要将任务分解为子任务,并使用不同的工具来完成每个子任务。\n\n你可以访问以下工具:\n{tool_desc}\n\n\n##输出格式\n\n请用与问题相同的语言回答,并使用以下格式:\n\n \nThought: 用户当前的语言是:(user's language)。我需要使用工具来帮助我回答问题。\nAction: 如果使用工具,则为工具名称(one of {tool_names})。\nAction Input: 输入给工具的内容,使用JSON格式表示kwargs(例如{{\"input\": \"hello world\", \"num_beams\": 5}}\n \n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n切勿用Markdown代码标记包围你的响应。如果需要,可以在响应中使用代码标记。\n\n请为Action Input使用有效的JSON格式。不要这样做{{\'input\': \'hello world\', \'num_beams\': 5}}。\n\n如果使用此格式,用户将以下面的格式进行回应:\n\n \nObservation: 工具响应\n \n\n你应该继续重复上述格式,直到你有足够的信息来回答问题而无需使用更多工具。此时,你必须使用以下两种格式之一进行回答:\n\n \nThought: 我可以不用任何工具来回答。我将使用用户的语言来回答。\nAnswer: [你的答案(与用户问题相同的语言)]\n \n\n \nThought: 我无法使用提供的工具回答问题。\nAnswer: [你的答案(与用户问题相同的语言)]\n \n\n##如果从工具中得到的回应是Empty Response,那么只需要回答“我不知道”,不需要额外回答别的内容。## 当前对话\n\n以下是当前对话,由人类和助手的消息交替组成。\n""")
react_chat_formatter = ReActChatFormatter.from_defaults(prefix_messages)
agentrunner = AgentRunner.from_llm(
llm=Settings.llm,
tools=tools,
react_chat_formatter=react_chat_formatter,
system_prompt=system_prompt,
verbose=True,
)
return agentrunner
# create the function calling worker for reasoning
# worker = FunctionCallingAgentWorker.from_tools(
# tools, verbose=True
# )
#
# # wrap the worker in the top-level planner
# return StructuredPlannerAgent(worker, tools)
@@ -1 +0,0 @@
STORAGE_DIR = "storage" # directory to cache the generated index
@@ -1,108 +0,0 @@
import os
from llama_index.core import SummaryIndex, SQLDatabase, VectorStoreIndex
from llama_index.core.indices.struct_store import SQLTableRetrieverQueryEngine
from llama_index.core.objects import SQLTableNodeMapping, ObjectIndex, SQLTableSchema
from llama_index.core.query_engine import RetrieverQueryEngine
from llama_index.core.response_synthesizers import ResponseMode
from llama_index.readers.database import DatabaseReader
from sqlalchemy import create_engine
from app.engine.prompt import text_qa_template, refine_template, summary_template, simple_template
from app.engine.retriever.HybridRetriever import HybridRetriever
from app.settings import get_node_postprocessors
def makeDescriptionByEngine(sql_database:SQLDatabase):
reader = DatabaseReader(sql_database)
table_names = sql_database.get_usable_table_names()
table_schema_objs = []
for table_name in table_names:
columns = sql_database.get_table_columns(table_name)
if len(columns) > 150:
continue
stats_txt = ""
if table_name == 'gongchengshuxing':
stats_txt = '该表中有以下属性:'
documents = reader.load_data(query='select name from gongchengshuxing')
for index in range(len(documents) if len(documents) < 30 else 30):
if index == 0:
continue
elif index > 1:
stats_txt += ','
stats_txt += documents[index].text.split(':')[1]
tbSchema = (SQLTableSchema(table_name=table_name, context_str=stats_txt))
table_schema_objs.append(tbSchema)
return table_schema_objs
def get_Retriever(index,**kwargs):
strEnableHybrid = os.getenv("HYBRID_ENABLED",'False')
bEnableHybrid = True if strEnableHybrid is not None and strEnableHybrid.title() == 'True' else False
if bEnableHybrid:
alpha = float(os.getenv("HYBRID_ALPHA", "0.5"))
retriever = HybridRetriever(index,alpha = alpha,**kwargs)
else:
retriever = index.as_retriever(**kwargs)
return retriever
sql_database = None
sql_obj_index = None
# Create a summary query engine
def create_summary_query_engine(top_k=3, use_reranker=False, filters=None):
global sql_obj_index
global sql_database
if sql_obj_index is None or sql_database is None:
sqlengine = create_engine(os.getenv("SQL_DATABASE_URL", ""))
sql_database = SQLDatabase(sqlengine)
table_schema_objs = makeDescriptionByEngine(sql_database)
table_node_mapping = SQLTableNodeMapping(sql_database)
sql_obj_index = ObjectIndex.from_objects(
table_schema_objs,
table_node_mapping,
index_cls=VectorStoreIndex,
)
# 创建SQL查询工具
sql_query_engine = SQLTableRetrieverQueryEngine(sql_database,
sql_obj_index.as_retriever(similarity_top_k=top_k),
verbose=True,
)
return sql_query_engine
# Create a summary query engine
def create_summary_query_engine(index, top_k=3, use_reranker=False, filters=None):
summary_index = SummaryIndex(index.vector_store.get_nodes(node_ids=None))
summary_query_engine = summary_index.as_query_engine(
response_mode=ResponseMode.TREE_SUMMARIZE,
use_async=True,
streaming=True,
)
return summary_query_engine
# Create a query engine
def create_query_engine(index, top_k=3, use_reranker=False, filters=None):
# 创建向量检索查询工具
postprocess = None
if use_reranker:
postprocess = get_node_postprocessors()
query_engine = RetrieverQueryEngine.from_args(
get_Retriever(index,
similarity_top_k=top_k,
filters=filters),
text_qa_template=text_qa_template,
refine_template=refine_template,
summary_template = summary_template,
simple_template = simple_template,
node_postprocessors=postprocess,
use_async=True,
streaming=True,
)
return query_engine
@@ -1,94 +0,0 @@
from dotenv import load_dotenv
load_dotenv()
import logging
import os
from app.engine.loaders import get_documents
from app.engine.vectordb import get_vector_store
from app.settings import init_settings
from app.engine.retriever.CHBM25Retriever import CHBM25Retriever
from llama_index.core.ingestion import IngestionPipeline
from llama_index.core.node_parser import SentenceSplitter
from llama_index.core.settings import Settings
from llama_index.core.storage import StorageContext
from llama_index.core.storage.docstore import SimpleDocumentStore
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger()
STORAGE_DIR = os.getenv("STORAGE_DIR", "storage")
def get_doc_store():
# If the storage directory is there, load the document store from it.
# If not, set up an in-memory document store since we can't load from a directory that doesn't exist.
if os.path.exists(STORAGE_DIR):
return SimpleDocumentStore.from_persist_dir(STORAGE_DIR)
else:
return SimpleDocumentStore()
def run_pipeline(docstore, vector_store, documents):
pipeline = IngestionPipeline(
transformations=[
SentenceSplitter(
chunk_size=Settings.chunk_size,
chunk_overlap=Settings.chunk_overlap,
),
Settings.embed_model,
],
docstore=docstore,
docstore_strategy="upserts_and_delete",
vector_store=vector_store,
)
# Run the ingestion pipeline and store the results
nodes = pipeline.run(show_progress=True, documents=documents)
return nodes
def persist_storage(docstore, vector_store):
storage_context = StorageContext.from_defaults(
docstore=docstore,
vector_store=vector_store,
)
storage_context.persist(STORAGE_DIR)
def persist_BMRetriever(vector_store):
STORAGE_DIR = os.getenv("BM_RETRIEVER_PATH", "storage_bm")
top_k = int(os.getenv("TOP_K", "3"))
bmRetriver = CHBM25Retriever.from_defaults(similarity_top_k=top_k,nodes=vector_store.get_nodes([]))
bmRetriver.persist(STORAGE_DIR)
def generate_datasource():
init_settings()
logger.info("Generate index for the provided data")
# Get the stores and documents or create new ones
documents = get_documents()
# Set private=false to mark the document as public (required for filtering)
for doc in documents:
doc.metadata["private"] = "false"
docstore = get_doc_store()
vector_store = get_vector_store()
# Run the ingestion pipeline
_ = run_pipeline(docstore, vector_store, documents)
# Build the index and persist storage
persist_storage(docstore, vector_store)
persist_BMRetriever(vector_store)
logger.info("Finished generating the index")
if __name__ == "__main__":
from phoenix.trace import using_project
with using_project(os.getenv("PHOENIX_PROJECT_NAME") + "_generate") as obj:
generate_datasource()
@@ -1,93 +0,0 @@
from llama_index.core import PromptTemplate
text_qa_template_str = (
"# 角色\n"
"你是一名博微造价工程数据查询助手,专精于电力工程文件中的信息。"
"你的职责是提供有关电力造价、造价编制软件、文件结构及相关数据的精准、客观的回答,"
"如同直接从文件中提取的内容。\n"
"知识库中已经导入一个工程的全部数据,请你站在当前工程的角度回答用户关于工程文件的问题。\n"
"例如:询问“此工程”指当前导入的工程。询问“此工程名称”指当前导入的工程的工程名称。\n"
"## 技能\n"
"### 技能 1: 数据查询与提供\n"
"- 准确回答所有关于电力工程造价的相关问题。\n"
"- 提供具体数据,如成本估算、材料清单、劳动力需求等。\n"
"- 确保提供的信息严格基于工程文档中的记录。\n"
"### 技能 2: 技术性解释\n"
"- 解释造价工程中的技术术语和概念。\n"
"- 为复杂的工程细节提供清晰易懂的说明。\n"
"## 约束\n"
"- 仅回答与电力工程造价文件相关的具体问题。\n"
"- 不进行任何超出文件内容的猜测或假设。\n"
"- 所有回答均基于文件内容,采用客观和技术性的语言。\n"
"- 请基于这些信息回答问题。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。\n"
"以下为上下文信息\n"
"---------------------\n"
"{context_str}\n"
"---------------------\n"
"请根据上下文信息而非先前知识回答我的问题或回复我的指令。前面的上下文信息可能有用,也可能没用,你需要从我给出的上下文信息中选出与我的问题最相关的那些,来为你的回答提供依据。回答一定要忠于原文,简洁但不丢信息,不要胡乱编造。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。我的问题或指令是什么语种,你就用什么语种回复。\n"
"如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"问题:{query_str}\n"
"你的回复: "
)
text_qa_template = PromptTemplate(text_qa_template_str)
refine_template_str = (
"这是原本的问题: {query_str}\n"
"我们已经提供了回答: {existing_answer}\n"
"现在我们有机会改进这个回答 "
"使用以下更多上下文(仅当有助于改进回答时使用)\n"
"如果新的上下文对回答没有影响,或者原来的回答已经正确,不要在上次回答的后边再加上多余的补充信息,直接返回原本的回答。\n"
"如果新的上下文对回答没有影响,或者原来的回答已经正确,不要在上次回答的后边再加上多余的补充信息,直接返回原本的回答。\n"
"------------\n"
"{context_msg}\n"
"------------\n"
"如果回答中已经包含有正确答案,不要返回多余的解释等信息,只返回正确答案\n"
"如果是表结构或者是数据库的相关内容,仅用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"改进的回答: "
)
refine_template = PromptTemplate(refine_template_str)
summary_template_str = (
"# 角色\n"
"你是一名博微造价工程数据查询助手,专精于电力工程文件中的信息。"
"你的职责是提供有关电力造价、造价编制软件、文件结构及相关数据的精准、客观的回答,"
"如同直接从文件中提取的内容。\n"
"## 技能\n"
"### 技能 1: 数据查询与提供\n"
"- 准确回答所有关于电力工程造价的相关问题。\n"
"- 提供具体数据,如成本估算、材料清单、劳动力需求等。\n"
"- 确保提供的信息严格基于工程文档中的记录。\n"
"### 技能 2: 技术性解释\n"
"- 解释造价工程中的技术术语和概念。\n"
"- 为复杂的工程细节提供清晰易懂的说明。\n"
"## 约束\n"
"- 仅回答与电力工程造价文件相关的具体问题。\n"
"- 不进行任何超出文件内容的猜测或假设。\n"
"- 所有回答均基于文件内容,采用客观和技术性的语言。\n"
"- 请基于这些信息回答问题。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。\n"
"来自多个来源的上下文信息如下。\n"
"---------------------\n"
"{context_str}\n"
"---------------------\n"
"鉴于来自多个来源的信息而非先验知识, "
"回答查询。\n"
"如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"Query: {query_str}\n"
"Answer: "
)
summary_template = PromptTemplate(summary_template_str)
simple_template_str = (
"{query_str}"
)
simple_template = PromptTemplate(simple_template_str)
@@ -1,71 +0,0 @@
import os
from llama_index.vector_stores.chroma import ChromaVectorStore
from llama_index.vector_stores.qdrant import QdrantVectorStore
from qdrant_client import qdrant_client
qclient = None
def get_qdrant_vector_store():
collection_name = os.getenv("VECTOR_STORE_COLLECTION", "default")
vector_store_path = os.getenv("VECTOR_STORE_PATH")
host=os.getenv("VECTOR_STORE_HOST", "127.0.0.1"),
port=int(os.getenv("VECTOR_STORE_PORT", "6333")),
if not vector_store_path or not host:
raise ValueError(
"Please provide either VECTOR_STORE_PATH or VECTOR_STORE_HOST and VECTOR_STORE_PORT"
)
# if VECTOR_STORE_PATH is set, use a local QdrantVectorStore from the path
# otherwise, use a remote QdrantVectorStore
global qclient
if qclient == None:
if vector_store_path:
qclient = qdrant_client.QdrantClient(
path=vector_store_path,
)
else:
qclient = qdrant_client.QdrantClient(
host=host,
port=port,
)
vector_store = QdrantVectorStore(client=qclient, collection_name=collection_name)
return vector_store
def get_chroma_vector_store():
collection_name = os.getenv("VECTOR_STORE_COLLECTION", "default")
vector_store_path = os.getenv("VECTOR_STORE_PATH")
# if VECTOR_STORE_PATH is set, use a local ChromaVectorStore from the path
# otherwise, use a remote ChromaVectorStore (ChromaDB Cloud is not supported yet)
if vector_store_path:
store = ChromaVectorStore.from_params(
persist_dir=vector_store_path, collection_name=collection_name,
collection_kwargs={"metadata":{"hnsw:space":"cosine"}},
)
else:
if not os.getenv("VECTOR_STORE_HOST") or not os.getenv("VECTOR_STORE_PORT"):
raise ValueError(
"Please provide either VECTOR_STORE_PATH or VECTOR_STORE_HOST and VECTOR_STORE_PORT"
)
store = ChromaVectorStore.from_params(
host=os.getenv("VECTOR_STORE_HOST"),
port=int(os.getenv("VECTOR_STORE_PORT")),
collection_name=collection_name,
collection_kwargs={"metadata":{"hnsw:space":"cosine"}},
)
return store
def get_vector_store():
store_type=os.getenv("VECTOR_STORE_TYPE")
store = None
match store_type:
case "chroma":
store = get_chroma_vector_store()
case "qdrant":
store = get_qdrant_vector_store()
case _:
raise ValueError(f"Invalid vector store type: {store_type}")
return store
+31 -12
View File
@@ -6,16 +6,28 @@ from llama_index.core.tools.query_engine import QueryEngineTool
from app.engine.engine import create_query_engine, create_summary_query_engine
from app.engine.index import get_index
from app.engine.prompt import ReActChatFormatter_messages, tree_summary_query_engine_tool_messages, \
query_engine_tool_messages, summary_query_tool_messages
#from app.engine.loaders.db import makeDescriptionByEngine
from app.engine.tools import ToolFactory
from app.api.routers.request.base import ProjectInfo
from llama_index.core.response_synthesizers import ResponseMode
def getPrjFalg(params:dict=None)->str:
if 'prjFalg' in params:
return params.get('prjFalg')
else:
prjFlag = ''
if params is not None:
prjFlag = ProjectInfo().prjFalg(params.get('projectname'))
return prjFlag
def get_chat_engine(filters=None, params=None):
def get_chat_engine(filters=None, params:dict=None):
system_prompt = os.getenv("SYSTEM_PROMPT")
top_k = int(os.getenv("TOP_K", "3"))
use_reranker = os.getenv("RERANK_ENABLED")
tools = []
# 创建SQL查询工具
# sql_query_engine = create_summary_query_engine(index)
# sql_query_tool = QueryEngineTool.from_defaults(query_engine=sql_query_engine,
@@ -25,33 +37,40 @@ def get_chat_engine(filters=None, params=None):
#tools.append(sql_query_tool)
# Add query tool if index exists
index = get_index()
index = get_index(getPrjFalg(params))
if index is not None:
summary_query_engine = create_summary_query_engine(index,top_k,use_reranker,filters)
summary_query_tool = QueryEngineTool.from_defaults( query_engine=summary_query_engine, name="summary_query_tool",
description="适用于任何需要进行全面总结、概括的要求。",
)
query_engine = create_query_engine(index,top_k,use_reranker,filters)
query_engine_tool = QueryEngineTool.from_defaults(query_engine=query_engine, name="zj_query_tool",
description="由博微公司编制的关于电力造价知识、电力造价编制软件知识和造价工程文件结构的知识库。适用于查询电力领域、电力造价领域、博微、博微电力、博微造价等业务等内容。如果本知识库没有直接答案但有解决思路的可以返回解决办法后建议使用“zjdata_query_tool”工具。",
description=summary_query_tool_messages,
)
tools.append(summary_query_tool)
query_engine = create_query_engine(index,top_k,use_reranker,filters,response_mode = ResponseMode.TREE_SUMMARIZE)
query_engine_tool = QueryEngineTool.from_defaults(query_engine=query_engine, name="zj_query_tool",
description=query_engine_tool_messages)
query_engine = create_query_engine(index,top_k,use_reranker,filters,response_mode = ResponseMode.TREE_SUMMARIZE)
query_engine_tool_1 = QueryEngineTool.from_defaults(query_engine=query_engine, name="zj_query_tool_1",
description=tree_summary_query_engine_tool_messages)
tools.append(query_engine_tool)
#tools.append(query_engine_tool_1)
#tools.append(summary_query_tool)
# Add additional tools
tools += ToolFactory.from_env()
prefix_messages = ("""您的设计旨在帮助完成各种任务,从回答问题到提供其他类型分析的摘要。\n\n##工具\n\n你可以访问各种工具。你有责任按照你认为合适的顺序使用这些工具来完成当前的任务。\n这可能需要将任务分解为子任务,并使用不同的工具来完成每个子任务。\n\n你可以访问以下工具:\n{tool_desc}\n\n\n##输出格式\n\n请用与问题相同的语言回答,并使用以下格式:\n\n \nThought: 用户当前的语言是:(user's language)。我需要使用工具来帮助我回答问题。\nAction: 如果使用工具,则为工具名称(one of {tool_names})。\nAction Input: 输入给工具的内容,使用JSON格式表示kwargs(例如{{\"input\": \"hello world\", \"num_beams\": 5}}\n \n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n请始终以Thought开始。\n\n切勿用Markdown代码标记包围你的响应。如果需要,可以在响应中使用代码标记。\n\n请为Action Input使用有效的JSON格式。不要这样做{{\'input\': \'hello world\', \'num_beams\': 5}}。\n\n如果使用此格式,用户将以下面的格式进行回应:\n\n \nObservation: 工具响应\n \n\n你应该继续重复上述格式,直到你有足够的信息来回答问题而无需使用更多工具。此时,你必须使用以下两种格式之一进行回答:\n\n \nThought: 我可以不用任何工具来回答。我将使用用户的语言来回答。\nAnswer: [你的答案(与用户问题相同的语言)]\n \n\n \nThought: 我无法使用提供的工具回答问题。\nAnswer: [你的答案(与用户问题相同的语言)]\n \n\n##如果从工具中得到的回应是Empty Response,那么只需要回答“我不知道”,不需要额外回答别的内容。## 当前对话\n\n以下是当前对话,由人类和助手的消息交替组成。\n""")
react_chat_formatter = ReActChatFormatter.from_defaults(prefix_messages)
react_chat_formatter = ReActChatFormatter.from_defaults(ReActChatFormatter_messages)
agentrunner = AgentRunner.from_llm(
llm=Settings.llm,
tools=tools,
react_chat_formatter=react_chat_formatter,
#react_chat_formatter=react_chat_formatter,
system_prompt=system_prompt,
verbose=True,
)
return agentrunner
# create the function calling worker for reasoning
# worker = FunctionCallingAgentWorker.from_tools(
# tools, verbose=True
+58 -8
View File
@@ -7,10 +7,31 @@ from llama_index.core.query_engine import RetrieverQueryEngine
from llama_index.core.response_synthesizers import ResponseMode
from llama_index.readers.database import DatabaseReader
from sqlalchemy import create_engine
from util.register import *
from app.engine.prompt import text_qa_template, refine_template, summary_template, simple_template
from app.engine.retriever.HybridRetriever import HybridRetriever
from app.settings import get_node_postprocessors
from app.engine.response.treeSummResponse import CustomTreeResponse
from llama_index.core.settings import Settings
from llama_index.core.indices.property_graph import LLMSynonymRetriever,VectorContextRetriever
from llama_index.core import PropertyGraphIndex
from app.engine.retriever.graphKeyWordRetriever import GraphKeyWordRetriever
ModelPlateCategory = '模型平台'
def get_node_postprocessors():
rerank_enabled = os.getenv("RERANK_ENABLED").title()
if rerank_enabled is None or rerank_enabled == 'False':
return []
Rerank_provider = os.getenv("RERANK_PROVIDER")
modelPaltCls = ClsRegister.get(ModelPlateCategory,Rerank_provider)
postprocess = None
if modelPaltCls is not None:
modelPalt = modelPaltCls()
postprocess = modelPalt.rerank()
else:
raise ValueError(f"Invalid rerank provider: {Rerank_provider}")
return postprocess
def makeDescriptionByEngine(sql_database:SQLDatabase):
reader = DatabaseReader(sql_database)
@@ -48,6 +69,13 @@ def get_Retriever(index,**kwargs):
retriever = index.as_retriever(**kwargs)
return retriever
def get_synthesizer():
return CustomTreeResponse(
llm=Settings.llm,
summary_template=summary_template,
use_async=True,
streaming=False,
)
sql_database = None
sql_obj_index = None
@@ -81,28 +109,50 @@ def create_summary_query_engine(index, top_k=3, use_reranker=False, filters=None
summary_query_engine = summary_index.as_query_engine(
response_mode=ResponseMode.TREE_SUMMARIZE,
use_async=True,
streaming=True,
streaming=False,
)
return summary_query_engine
# Create a query engine
def create_query_engine(index, top_k=3, use_reranker=False, filters=None):
def create_query_engine(index,top_k=3, use_reranker=False, filters=None, response_mode=None):
# 创建向量检索查询工具
postprocess = None
if use_reranker:
postprocess = get_node_postprocessors()
query_engine = RetrieverQueryEngine.from_args(
get_Retriever(index,
llm_query = os.getenv('LLM_QUERY_WAY','rag')
if llm_query == 'graph':
graphIndex:PropertyGraphIndex = index
keyWord_retriver = GraphKeyWordRetriever(graphIndex.property_graph_store,
include_text=False
)
if graphIndex.property_graph_store.supports_vector_queries:
vector_store = None
else:
vector_store = graphIndex.vector_store
vector_retriver = VectorContextRetriever(graphIndex.property_graph_store,
vector_store = vector_store,
embed_model=Settings.embed_model,
similarity_top_k=top_k,
filters=filters),
include_text=False
)
retriever = graphIndex.as_retriever(sub_retrievers=[keyWord_retriver,vector_retriver])
else:
retriever = get_Retriever(index,
similarity_top_k=top_k,
filters=filters)
query_engine = RetrieverQueryEngine.from_args(
retriever = retriever,
text_qa_template=text_qa_template,
refine_template=refine_template,
summary_template = summary_template,
simple_template = simple_template,
node_postprocessors=postprocess,
use_async=True,
streaming=True,
streaming=False,
response_mode = response_mode
)
return query_engine
+69 -23
View File
@@ -5,39 +5,41 @@ load_dotenv()
import logging
import os
from app.engine.loaders import get_documents
from app.engine.vectordb import get_vector_store
from app.engine.loaders import get_document_Types, get_documents,getProjectInfos
from app.engine.vectordb import get_vector_store,get_Neo4j_Graph_Store
from app.settings import init_settings
from app.engine.retriever.CHBM25Retriever import CHBM25Retriever
from llama_index.core.ingestion import IngestionPipeline
from llama_index.core.node_parser import SentenceSplitter
from llama_index.core.node_parser import SentenceSplitter,MarkdownNodeParser
from llama_index.core.settings import Settings
from llama_index.core.storage import StorageContext
from llama_index.core.storage.docstore import SimpleDocumentStore
from llama_index.core import PropertyGraphIndex
from app.engine.graph.extractor import PrjGraphExtractor
from app.engine.graph.graphStore import RAGPropertyGraphStore
logging.basicConfig(level=logging.INFO)
logger = logging.getLogger()
STORAGE_DIR = os.getenv("STORAGE_DIR", "storage")
def get_doc_store():
def get_doc_store(docType:str):
# If the storage directory is there, load the document store from it.
# If not, set up an in-memory document store since we can't load from a directory that doesn't exist.
if os.path.exists(STORAGE_DIR):
return SimpleDocumentStore.from_persist_dir(STORAGE_DIR)
storeDir = os.path.join(STORAGE_DIR,docType)
if os.path.exists(storeDir):
return SimpleDocumentStore.from_persist_dir(storeDir)
else:
return SimpleDocumentStore()
def run_pipeline(docstore, vector_store, documents):
pipeline = IngestionPipeline(
transformations=[
SentenceSplitter(
chunk_size=Settings.chunk_size,
chunk_overlap=Settings.chunk_overlap,
),
#SentenceSplitter(
#chunk_size=Settings.chunk_size,
#chunk_overlap=Settings.chunk_overlap,
#),
#MarkdownNodeParser(),
Settings.embed_model,
],
docstore=docstore,
@@ -47,10 +49,8 @@ def run_pipeline(docstore, vector_store, documents):
# Run the ingestion pipeline and store the results
nodes = pipeline.run(show_progress=True, documents=documents)
return nodes
def persist_storage(docstore, vector_store):
storage_context = StorageContext.from_defaults(
docstore=docstore,
@@ -58,25 +58,25 @@ def persist_storage(docstore, vector_store):
)
storage_context.persist(STORAGE_DIR)
def persist_BMRetriever(vector_store):
STORAGE_DIR = os.getenv("BM_RETRIEVER_PATH", "storage_bm")
top_k = int(os.getenv("TOP_K", "3"))
bmRetriver = CHBM25Retriever.from_defaults(similarity_top_k=top_k,nodes=vector_store.get_nodes([]))
nodes = vector_store.get_nodes([])
top_k = min(int(os.getenv("TOP_K", "3")),len(nodes))
bmRetriver = CHBM25Retriever.from_defaults(similarity_top_k=top_k,nodes = nodes)
bmRetriver.persist(STORAGE_DIR)
def generate_datasource():
init_settings()
logger.info("Generate index for the provided data")
# Get the stores and documents or create new ones
documents = get_documents()
docTypes = get_document_Types()
for docType in docTypes:
documents = get_documents(docType)
# Set private=false to mark the document as public (required for filtering)
for doc in documents:
doc.metadata["private"] = "false"
docstore = get_doc_store()
vector_store = get_vector_store()
docstore = get_doc_store(docType)
vector_store = get_vector_store(docType)
# Run the ingestion pipeline
_ = run_pipeline(docstore, vector_store, documents)
@@ -87,8 +87,54 @@ def generate_datasource():
logger.info("Finished generating the index")
class PropertyGraphChache:
def generate(self):
GRAPH_STORE_TYPE = os.getenv("GRAPH_STORE_TYPE", "")
GRAPH_STORAGE_DIR = os.getenv("GRAPH_STORAGE_PATH", "storage_graph")
prjInfos = getProjectInfos()
for prjInfo in prjInfos:
prjFlag = prjInfo['flag']
prjName = prjInfo['name']
chche_Path = GRAPH_STORAGE_DIR + f'/{prjFlag}'
if GRAPH_STORE_TYPE == 'neo4j':
self.neo4jProertyGraph(prjName,prjFlag,chche_Path)
else:
self.simplePropertyGraph(prjName,prjFlag,chche_Path)
def simplePropertyGraph(self,prjName:str,prjFlag:str,filePath:str):
documents = get_documents(prjFlag)
storeContext = StorageContext.from_defaults(vector_store=get_vector_store(prjFlag),
property_graph_store = RAGPropertyGraphStore())
index = PropertyGraphIndex(
nodes =documents,
kg_extractors = [PrjGraphExtractor(prjName)],
embed_model = Settings.embed_model,
storage_context = storeContext,
show_progress= True
)
os.makedirs(filePath,exist_ok = True)
index.storage_context.persist(persist_dir = filePath)
def neo4jProertyGraph(self,prjName:str,prjFlag:str,filePath:str):
neo4jStore =get_Neo4j_Graph_Store(prjFlag)
documents = get_documents(prjFlag)
PropertyGraphIndex(
nodes =documents,
property_graph_store = neo4jStore,
kg_extractors = [PrjGraphExtractor(prjName)],
embed_model = Settings.embed_model,
show_progress= True
)
if __name__ == "__main__":
init_settings()
llm_query = os.getenv('LLM_QUERY_WAY','rag')
from phoenix.trace import using_project
with using_project(os.getenv("PHOENIX_PROJECT_NAME") + "_generate") as obj:
if llm_query == 'graph':
PropertyGraphChache().generate()
else:
generate_datasource()
+231
View File
@@ -0,0 +1,231 @@
import os
from llama_index.core.schema import TransformComponent, BaseNode
from llama_index.core.graph_stores.types import (
KG_NODES_KEY,
KG_RELATIONS_KEY,
)
from app.engine.loaders.markdownReader import ChunkMarkdownReader
from app.engine.graph.graphTypes import *
import uuid
IdField = '_id'
nodeTypeField = 'nodeType'
parentIDField = 'parentId'
class Record:
def __init__(self,id:str,tableName:str,property:dict) -> None:
self._childs = []
self._id = id
self._property:dict = property
self._tableName = tableName
def add(self,rcd:'Record'):
self._childs.append(rcd)
@property
def Property(self):
return self._property
@property
def Id(self):
return self._id
@property
def Name(self):
for name,value in self._property.items():
if '名称' in name:
return value
raise ValueError('记录名称为空')
@property
def Label(self):
if '工程属性' in self._tableName:
label = '属性项'
else:
label = self.Property[nodeTypeField] if nodeTypeField in self.Property else self.Name
label = label + ''
return label
@property
def HasChild(self):
return len(self._childs) > 0
def childCount(self):
return len(self._childs)
def child(self,index:int):
return self._childs[index]
class RecordTreeMake:
def __init__(self,tableName:str,records:list) -> None:
self._records = records
self._tableName = tableName
def make(self)->list[Record]:
rcdMaps:dict[str,Record] = {}
for record in self._records:
parid= ''
if parentIDField in record:
parid = record[parentIDField]
id = record[IdField] if IdField in record else str(uuid.uuid1())
if parid in rcdMaps:
parRcd = rcdMaps[parid]
parRcd.add(Record(id,self._tableName,record))
else:
rcdMaps[id] = Record(id,self._tableName,record)
return list(rcdMaps.values())
class PrjGraphExtractor(TransformComponent):
ProjectName:str
_nodeMaps = {}
_prjID = ''
def __init__(self,PrjName:str):
super().__init__(ProjectName = PrjName)
def __call__(
self, llama_nodes: list[BaseNode], **kwargs
) -> list[BaseNode]:
if len(llama_nodes) > 0:
self._addPrjNode(llama_nodes[0])
for llama_node in llama_nodes:
fileName = self._getFileName(llama_node)
if fileName == '工程属性':
self._dealAttributeNode(llama_node)
else:
self._dealCommonNode(llama_node)
return llama_nodes
def _dealCommonNode(self,llama_node:BaseNode):
fileName = self._getFileName(llama_node)
existing_nodes:list = llama_node.metadata.pop(KG_NODES_KEY, [])
existing_relations:list = llama_node.metadata.pop(KG_RELATIONS_KEY, [])
records:dict[str,list] = self._getRecordNode(llama_node)
fInfos = fileName.split('_')
if len(fInfos) == 1:
fileID = self._addTableNode(existing_nodes = existing_nodes,name=fInfos[0], label=fInfos[0])
elif len(fInfos) == 2:
fileID = self._addTableNode(existing_nodes = existing_nodes,name=fInfos[1], label=fInfos[0])
else:
raise ValueError("文件名存在多个下划线")
rdMake = RecordTreeMake(fileName,records)
rcds:list[Record] = rdMake.make()
for record in rcds:
self._make_RecordEdge(existing_nodes = existing_nodes,
existing_relations = existing_relations,
fileID = fileID,
rcd = record)
existing_relations.append(
RagRelation(
label="包含",
source_id= self._prjID,
target_id= fileID
)
)
llama_node.metadata[KG_NODES_KEY] = existing_nodes
llama_node.metadata[KG_RELATIONS_KEY] = existing_relations
def _dealAttributeNode(self,llama_node:BaseNode):
fileName = self._getFileName(llama_node)
existing_nodes:list = llama_node.metadata.pop(KG_NODES_KEY, [])
existing_relations:list = llama_node.metadata.pop(KG_RELATIONS_KEY, [])
records:dict[str,list] = self._getRecordNode(llama_node)
fileID = self._addTableNode(existing_nodes = existing_nodes,name=fileName, label=fileName)
rdMake = RecordTreeMake(fileName,records)
rcds:list[Record] = rdMake.make()
for record in rcds:
attID = self._add_RecorNode(existing_nodes = existing_nodes,rcd = record)
existing_relations.append(
RagRelation(
label="聚合",
source_id= fileID,
target_id= attID
)
)
existing_relations.append(
RagRelation(
label="包含",
source_id= self._prjID,
target_id= fileID
)
)
llama_node.metadata[KG_NODES_KEY] = existing_nodes
llama_node.metadata[KG_RELATIONS_KEY] = existing_relations
def _getRecordNode(self,llama_node:BaseNode):
content = llama_node.get_content()
rd = ChunkMarkdownReader()
rd.markdown_to_tups(content)
records = rd.records()
return records
def _getFileName(self,llama_node:BaseNode):
meta = llama_node.metadata
fileName:str = os.path.splitext(meta['file_name'])[0]
return fileName
def _addPrjNode(self,llama_node:BaseNode):
existing_nodes:list = llama_node.metadata.pop(KG_NODES_KEY, [])
self._prjID = self._addTableNode(existing_nodes = existing_nodes,name=self.ProjectName,label=self.ProjectName)
llama_node.metadata[KG_NODES_KEY] = existing_nodes
def _addTableNode(self,existing_nodes:list,name:str,label:str):
return self._add_Node(existing_nodes,name,label,str(uuid.uuid1()))
def _add_RecorNode(self,existing_nodes:list,rcd:Record):
return self._add_Node(existing_nodes,rcd.Name,rcd.Label,rcd.Id,rcd.Property)
def _add_Node(self,existing_nodes:list,name:str,label:str,defaultid:str,property:dict= {}):
id:str = ''
if name in self._nodeMaps:
nodes:list[RagEntityNode] = self._nodeMaps[name]
for node in nodes:
if node.properties == property and node.name == name and node.label == label:
id = node.id
break
if id =='':
id = defaultid
newNode = RagEntityNode(name = name,label=label,properties = property,uid = id)
existing_nodes.append(newNode)
if name in self._nodeMaps:
nodes:list[RagEntityNode] = self._nodeMaps[name]
nodes.append(newNode)
else:
self._nodeMaps[name] = [newNode]
return id
def _make_RecordEdge(self,existing_nodes:list,existing_relations:list,fileID:str,rcd:Record,parID:str = ''):
rcdID = self._add_RecorNode(existing_nodes = existing_nodes,rcd = rcd)
if fileID!='':
existing_relations.append(
RagRelation(
label="子级",
source_id= fileID,
target_id= rcdID
)
)
if parID!='':
existing_relations.append(
RagRelation(
label="子级",
source_id= parID,
target_id= rcdID
)
)
if rcd.HasChild:
for i in range(rcd.childCount()):
child = rcd.child(i)
self._make_RecordEdge(existing_nodes,existing_relations,'',child,rcdID)
+60
View File
@@ -0,0 +1,60 @@
from typing import Any, List, Dict, Sequence, Tuple, Optional
from llama_index.core.graph_stores.simple_labelled import SimplePropertyGraphStore
from llama_index.core.graph_stores.types import LabelledNode,ChunkNode,LabelledPropertyGraph
from app.engine.graph.graphTypes import *
class RAGPropertyGraphStore(SimplePropertyGraphStore):
@classmethod
def from_dict(
cls,
data: dict,
) -> "SimplePropertyGraphStore":
"""Load from dict."""
# need to load nodes manually
node_dicts = data["nodes"]
relation_dicts = data["relations"]
kg_nodes: Dict[str, LabelledNode] = {}
kg_relations: Dict[str, LabelledNode] = {}
for id, node_dict in node_dicts.items():
if "name" in node_dict:
kg_nodes[id] = RagEntityNode.model_validate(node_dict)
elif "text" in node_dict:
kg_nodes[id] = ChunkNode.model_validate(node_dict)
else:
raise ValueError(f"Could not infer node type for data: {node_dict!s}")
for id, node_dict in relation_dicts.items():
kg_relations[id] = RagRelation.model_validate(node_dict)
# clear the nodes, to load later
data["nodes"] = {}
data["relations"] = {}
# load the graph
graph = LabelledPropertyGraph.model_validate(data)
# add the node back
graph.nodes = kg_nodes
graph.relations = kg_relations
return cls(graph)
def save_networkx_graph(self, name: str = "kg.html") -> None:
"""Display the graph store, useful for debugging."""
import networkx as nx
G = nx.DiGraph()
for node in self.graph.nodes.values():
if isinstance(node,EntityNode):
G.add_node(node.id, label=node.name)
for triplet in self.graph.triplets:
G.add_edge(triplet[0], triplet[2], label=triplet[1])
# save to html file
from pyvis.network import Network
net = Network(notebook=False, directed=True)
net.from_nx(G)
net.write_html(name)
+38
View File
@@ -0,0 +1,38 @@
from llama_index.core.graph_stores.types import (
EntityNode,
Relation
)
class RagEntityNode(EntityNode):
uid : str
def __str__(self) -> str:
"""Return the string representation of the node."""
if self.properties:
prop = self.properties
if 'triplet_source_id' in prop:
prop.pop('triplet_source_id')
if len(prop) > 0:
return f"{self.name} ({prop})"
return self.name
@property
def id(self) -> str:
"""Get the node id."""
#return self.name.replace('"', " ")
return self.uid
class RagRelation(Relation):
def __str__(self) -> str:
"""Return the string representation of the relation."""
if self.properties:
prop = self.properties
if 'triplet_source_id' in prop:
prop.pop('triplet_source_id')
if len(prop) > 0:
return f"{self.label} ({prop})"
return self.label
@property
def id(self) -> str:
"""Get the relation id."""
return self.label
+88
View File
@@ -0,0 +1,88 @@
from llama_index.core.indices.property_graph import LLMSynonymRetriever,VectorContextRetriever,PGRetriever
from llama_index.core.indices.property_graph.transformations.schema_llm import *
from llama_index.core import SimpleDirectoryReader
from llama_index.core import settings
from llama_index.core import PropertyGraphIndex,KnowledgeGraphIndex
from typing import List,Tuple,Literal
from app.settings import init_settings
import os
from llama_index.core.storage.storage_context import StorageContext
from llama_index.core import load_index_from_storage
from app.observability import init_observability
from app.engine.vectordb import get_Neo4j_Graph_Store,get_vector_store
from llama_index.core.response_synthesizers import ResponseMode
from util.register import *
from llama_index.core.query_engine import RetrieverQueryEngine
from app.engine.prompt import text_qa_template, refine_template, summary_template, simple_template
from app.engine.engine import get_node_postprocessors
from app.engine.graph.graphStore import RAGPropertyGraphStore
from app.engine.retriever.graphKeyWordRetriever import GraphKeyWordRetriever
class PropertyGraph:
def __init__(self,prjFlag:str) -> None:
self._prjFlag = prjFlag
def create_query_engine(self,retriever):
postprocess = get_node_postprocessors()
query_engine = RetrieverQueryEngine.from_args(
retriever = retriever,
text_qa_template=text_qa_template,
refine_template=refine_template,
summary_template = summary_template,
simple_template = simple_template,
node_postprocessors=postprocess,
use_async=True,
streaming=False,
response_mode = ResponseMode.TREE_SUMMARIZE
)
return query_engine
def getPropertyGraphIndex(self):
GRAPH_STORE_TYPE = os.getenv("GRAPH_STORE_TYPE", "")
if GRAPH_STORE_TYPE == 'neo4j':
index = PropertyGraphIndex.from_existing(property_graph_store= get_Neo4j_Graph_Store(self._prjFlag))
else:
GRAPH_STORAGE_DIR = os.getenv("GRAPH_STORAGE_PATH", "storage_graph")
prjCachePath = GRAPH_STORAGE_DIR + f"/{self._prjFlag}"
if not os.path.exists(prjCachePath):
return None
storeContext = StorageContext.from_defaults(persist_dir = prjCachePath,vector_store = get_vector_store(self._prjFlag),
property_graph_store = RAGPropertyGraphStore.from_persist_dir(prjCachePath))
index = load_index_from_storage(storeContext)
return index
def query(self,query_str:str):
index = self.getPropertyGraphIndex()
synonym_retriver = GraphKeyWordRetriever(index.property_graph_store,
include_text=False
)
if index.property_graph_store.supports_vector_queries:
vector_store = None
else:
vector_store = index.vector_store
vector_retriver = VectorContextRetriever(index.property_graph_store,
vector_store = vector_store,
embed_model=settings.Settings.embed_model,
similarity_top_k=10,
include_text=False
)
retriever = index.as_retriever(sub_retrievers=[synonym_retriver,vector_retriver])
query_engine = self.create_query_engine(retriever)
response = query_engine.query(query_str)
print(response)
return str(response)
if __name__ == "__main__":
init_settings()
init_observability()
graph = PropertyGraph('projects_0ffaf7fb-8a61-46e2-97a2-8f924e9560a7')
graph.query('工程属性表有哪些字段')
+31 -13
View File
@@ -1,22 +1,40 @@
import logging
import logging,os
from llama_index.core.indices import VectorStoreIndex
from app.engine.vectordb import get_vector_store
from app.engine.vectordb import get_vector_store,get_Neo4j_Graph_Store
from typing import Dict,Any
from llama_index.core import PropertyGraphIndex
from llama_index.core.storage.storage_context import StorageContext
from llama_index.core import load_index_from_storage
from app.engine.graph.graphStore import RAGPropertyGraphStore
logger = logging.getLogger("uvicorn")
index = None
def get_index(params=None):
global index
if index is None:
def get_index(prjFlag:str):
if prjFlag is None or prjFlag == '':
raise ValueError('无效的工程标识')
logger.info("Connecting vector store...")
store = get_vector_store()
# Load the index from the vector store
# If you are using a vector store that doesn't store text,
# you must load the index from both the vector store and the document store
index = None
llm_query = os.getenv('LLM_QUERY_WAY')
if llm_query == 'graph':
index = getPropertyGraphIndex(prjFlag)
else:
store = get_vector_store(prjFlag)
index = VectorStoreIndex.from_vector_store(store)
logger.info("Finished load index from vector store.")
return index
def getPropertyGraphIndex(prjFlag:str):
GRAPH_STORE_TYPE = os.getenv("GRAPH_STORE_TYPE", "")
if GRAPH_STORE_TYPE == 'neo4j':
index = PropertyGraphIndex.from_existing(property_graph_store= get_Neo4j_Graph_Store(prjFlag))
else:
GRAPH_STORAGE_DIR = os.getenv("GRAPH_STORAGE_PATH", "storage_graph")
prjCachePath = GRAPH_STORAGE_DIR + f"/{prjFlag}"
if not os.path.exists(prjCachePath):
return None
storeContext = StorageContext.from_defaults(persist_dir = prjCachePath,vector_store = get_vector_store(prjFlag),
property_graph_store = RAGPropertyGraphStore.from_persist_dir(prjCachePath))
index = load_index_from_storage(storeContext)
return index
@@ -1,40 +0,0 @@
import logging
import yaml
from app.engine.loaders.db import DBLoaderConfig, get_db_documents
from app.engine.loaders.file import FileLoaderConfig, get_file_documents
from app.engine.loaders.web import WebLoaderConfig, get_web_documents
logger = logging.getLogger(__name__)
def load_configs():
with open("config/loaders.yaml") as f:
configs = yaml.safe_load(f)
return configs
def get_documents():
documents = []
config = load_configs()
if config is None or len(config.items()) == 0:
return documents
for loader_type, loader_config in config.items():
logger.info(
f"Loading documents from loader: {loader_type}, config: {loader_config}"
)
loader_config = loader_config or []
match loader_type:
case "file":
document = get_file_documents(FileLoaderConfig(**loader_config))
case "web":
document = get_web_documents(WebLoaderConfig(**loader_config))
case "db":
document = get_db_documents(configs=[DBLoaderConfig(**cfg) for cfg in loader_config])
case _:
raise ValueError(f"Invalid loader type: {loader_type}")
documents.extend(document)
return documents
@@ -1,140 +0,0 @@
import logging
from typing import Any, List, Optional
from llama_index.core import SQLDatabase, Document
from llama_index.readers.database import DatabaseReader
from pydantic import BaseModel
from sqlalchemy import create_engine, text
from sqlalchemy.engine import Engine
logger = logging.getLogger(__name__)
class CustomDatabaseReader(DatabaseReader):
"""Simple Database reader.
Concatenates each row into Document used by LlamaIndex.
Args:
sql_database (Optional[SQLDatabase]): SQL database to use,
including table names to specify.
See :ref:`Ref-Struct-Store` for more details.
OR
engine (Optional[Engine]): SQLAlchemy Engine object of the database connection.
OR
uri (Optional[str]): uri of the database connection.
OR
scheme (Optional[str]): scheme of the database connection.
host (Optional[str]): host of the database connection.
port (Optional[int]): port of the database connection.
user (Optional[str]): user of the database connection.
password (Optional[str]): password of the database connection.
dbname (Optional[str]): dbname of the database connection.
Returns:
DatabaseReader: A DatabaseReader object.
"""
def __init__(
self,
sql_database: Optional[SQLDatabase] = None,
engine: Optional[Engine] = None,
uri: Optional[str] = None,
scheme: Optional[str] = None,
host: Optional[str] = None,
port: Optional[str] = None,
user: Optional[str] = None,
password: Optional[str] = None,
dbname: Optional[str] = None,
*args: Any,
**kwargs: Any,
) -> None:
"""Initialize with parameters."""
if sql_database:
self.sql_database = sql_database
elif engine:
self.sql_database = SQLDatabase(engine, *args, **kwargs)
elif uri:
self.uri = uri
self.sql_database = SQLDatabase.from_uri(uri, *args, **kwargs)
elif scheme and host and port and user and password and dbname:
uri = f"{scheme}://{user}:{password}@{host}:{port}/{dbname}"
self.uri = uri
self.sql_database = SQLDatabase.from_uri(uri, *args, **kwargs)
else:
raise ValueError(
"You must provide either a SQLDatabase, "
"a SQL Alchemy Engine, a valid connection URI, or a valid "
"set of credentials."
)
def load_data(self, query: str, explanation: str) -> List[Document]:
"""Query and load data from the Database, returning a list of Documents.
Args:
query (str): Query parameter to filter tables and rows.
explanation (str): Explanation for the query to be included in the document.
Returns:
List[Document]: A list of Document objects.
"""
dco_str = explanation + "\n"
with self.sql_database.engine.connect() as connection:
if query is None:
raise ValueError("A query parameter is necessary to filter the data")
else:
result = connection.execute(text(query))
dco_str += ", ".join(
[f"{entry}" for entry in result.keys()]
) + "\n"
for item in result.fetchall():
# Fetch each item
record_str = ", ".join(
[f"{entry}" for col, entry in zip(result.keys(), item)]
)
dco_str += record_str + "\n"
doc = Document(text=dco_str)
doc.metadata["name"] = query
doc.metadata["context"] = query
doc.metadata["file_type"] = "application/vnd.ms-excel"
return [doc]
class DBLoaderConfig(BaseModel):
uri: str
queries: List[dict]
def get_db_documents(configs: list[DBLoaderConfig]):
docs = []
if len(configs) == 0 or configs[0].uri == "":
logger.warning(
f"Failed to load database, error message: uri is empty. Return as empty document list."
)
return docs
metadata = {
'file_type': 'application/booway.document.zj',
}
for entry in configs:
engine = create_engine(entry.uri)
sql_database = SQLDatabase(engine)
loader = CustomDatabaseReader(sql_database)
for query_dict in entry.queries:
query = query_dict.get("sql", "")
explanation = query_dict.get("explanation", "")
logger.info(f"Loading data from database with query: {query}")
documents = loader.load_data(query=query, explanation=explanation)
docs.extend(documents)
return docs
@@ -1,88 +0,0 @@
import os
import logging
from typing import Dict
from llama_index.core.readers.base import BaseReader
from llama_index.core.readers.json import JSONReader
from llama_parse import LlamaParse
from pydantic import BaseModel, validator
logger = logging.getLogger(__name__)
class FileLoaderConfig(BaseModel):
data_dir: str = "data"
use_llama_parse: bool = False
@validator("data_dir")
def data_dir_must_exist(cls, v):
if not os.path.isdir(v):
raise ValueError(f"Directory '{v}' does not exist")
return v
def llama_parse_parser():
if os.getenv("LLAMA_CLOUD_API_KEY") is None:
raise ValueError(
"LLAMA_CLOUD_API_KEY environment variable is not set. "
"Please set it in .env file or in your shell environment then run again!"
)
parser = LlamaParse(
result_type="markdown",
verbose=True,
language="en",
ignore_errors=False,
)
return parser
def llama_parse_extractor() -> Dict[str, LlamaParse]:
from llama_parse.utils import SUPPORTED_FILE_TYPES
parser = llama_parse_parser()
return {file_type: parser for file_type in SUPPORTED_FILE_TYPES}
def llama_local_extractor() -> Dict[str, BaseReader]:
return {".json" : JSONReader(clean_json=False,levels_back=0)}
def get_file_documents(config: FileLoaderConfig):
from llama_index.core.readers import SimpleDirectoryReader
try:
file_extractor = None
if config.use_llama_parse:
# LlamaParse is async first,
# so we need to use nest_asyncio to run it in sync mode
import nest_asyncio
nest_asyncio.apply()
file_extractor = llama_parse_extractor()
else:
file_extractor = llama_local_extractor()
reader = SimpleDirectoryReader(
config.data_dir,
recursive=True,
filename_as_id=True,
raise_on_error=True,
file_extractor=file_extractor,
)
return reader.load_data()
except Exception as e:
import sys
import traceback
# Catch the error if the data dir is empty
# and return as empty document list
_, _, exc_traceback = sys.exc_info()
function_name = traceback.extract_tb(exc_traceback)[-1].name
if function_name == "_add_files":
logger.warning(
f"Failed to load file documents, error message: {e} . Return as empty document list."
)
return []
else:
# Raise the error if it is not the case of empty data dir
raise e
@@ -1,37 +0,0 @@
import os
import json
from pydantic import BaseModel, Field
class CrawlUrl(BaseModel):
base_url: str
prefix: str
max_depth: int = Field(default=1, ge=0)
class WebLoaderConfig(BaseModel):
driver_arguments: list[str] = Field(default=None)
urls: list[CrawlUrl] = []
def get_web_documents(config: WebLoaderConfig):
from llama_index.readers.web import WholeSiteReader
from selenium import webdriver
from selenium.webdriver.chrome.options import Options
options = Options()
driver_arguments = config.driver_arguments or []
for arg in driver_arguments:
options.add_argument(arg)
docs = []
urls = config.urls or []
for url in config.urls:
scraper = WholeSiteReader(
prefix=url.prefix,
max_depth=url.max_depth,
driver=webdriver.Chrome(options=options),
)
docs.extend(scraper.load_data(url.base_url))
return docs
+75 -5
View File
@@ -1,26 +1,96 @@
import logging
import yaml
from app.engine.loaders.db import DBLoaderConfig, get_db_documents
from app.engine.loaders.file import FileLoaderConfig, get_file_documents
from app.engine.loaders.web import WebLoaderConfig, get_web_documents
from app.engine.loaders.file import getProjectName
import os
logger = logging.getLogger(__name__)
def load_configs():
with open("config/loaders.yaml") as f:
with open("config/loaders.yaml",encoding='utf-8') as f:
configs = yaml.safe_load(f)
return configs
def path_difference(path1:str, path2:str):
import os
path1 = os.path.abspath(path1)
path2 = os.path.abspath(path2)
def get_documents():
path1_parts = path1.split(os.path.sep)
path2_parts = path2.split(os.path.sep)
for i, part in enumerate(path1_parts):
if part != path2_parts[i]:
break
else:
i += 1
pathKey = ''
for j in range(i,len(path2_parts)):
pathKey+=path2_parts[j] + '_'
return pathKey[0:-1]
def getFileCacahePath():
rootPath = 'data'
configs = load_configs()
if configs is not None and len(configs.items()) > 0:
for loader_type, loader_config in configs.items():
if loader_type == "file":
rootPath = FileLoaderConfig(**loader_config).data_dir
break
return rootPath
def get_document_Types():
rootPath = getFileCacahePath()
types = []
dirStack = [rootPath]
while len(dirStack) > 0:
curDir = dirStack.pop()
dirs = [os.path.join(curDir, d) for d in os.listdir(curDir) if os.path.isdir(os.path.join(curDir, d))]
if len(dirs) > 0:
for dir in dirs:
dirStack.append(dir)
else:
types.append(path_difference(rootPath,curDir))
return types
def getProjectInfos():
config = load_configs()
if config is None or len(config.items()) == 0:
return None
prjDir = None
for loader_type, loader_config in config.items():
if loader_config.get('enable', True):
loader_config = loader_config or []
config = FileLoaderConfig(**loader_config)
prjDir = config.data_dir
break
if prjDir is None:
return None
prjInfos = []
prjFlags = get_document_Types()
for prjFlag in prjFlags:
fileDir = os.path.join(config.data_dir,prjFlag.replace('_','\\'))
prjInfo = {}
prjInfo['flag'] = prjFlag
prjInfo['name'] = getProjectName(fileDir)
prjInfos.append(prjInfo)
return prjInfos
def get_documents(docType:str):
documents = []
config = load_configs()
if config is None or len(config.items()) == 0:
return documents
for loader_type, loader_config in config.items():
if loader_config.get('enable', True): # 检查 enable 字段
logger.info(
f"Loading documents from loader: {loader_type}, config: {loader_config}"
)
@@ -28,7 +98,7 @@ def get_documents():
loader_config = loader_config or []
match loader_type:
case "file":
document = get_file_documents(FileLoaderConfig(**loader_config))
document = get_file_documents(FileLoaderConfig(**loader_config),docType)
case "web":
document = get_web_documents(WebLoaderConfig(**loader_config))
case "db":
+19 -30
View File
@@ -2,17 +2,14 @@ import logging
from typing import Any, List, Optional
from llama_index.core import SQLDatabase, Document
from llama_index.core.objects import SQLTableSchema
from llama_index.core.readers.base import BaseReader
from llama_index.readers.database import DatabaseReader
from pydantic import BaseModel
from sqlalchemy import create_engine
from sqlalchemy import text
from sqlalchemy import create_engine, text
from sqlalchemy.engine import Engine
logger = logging.getLogger(__name__)
class CustomDatabaseReader(BaseReader):
class CustomDatabaseReader(DatabaseReader):
"""Simple Database reader.
Concatenates each row into Document used by LlamaIndex.
@@ -86,18 +83,19 @@ class CustomDatabaseReader(BaseReader):
List[Document]: A list of Document objects.
"""
dco_str = ""
with self.sql_database.engine.connect() as connection:
if query is None:
raise ValueError("A query parameter is necessary to filter the data")
else:
result = connection.execute(text(query))
dco_str = ", ".join(
dco_str += ", ".join(
[f"{entry}" for entry in result.keys()]
)
) + "\n"
for item in result.fetchall():
# fetch each item
# Fetch each item
record_str = ", ".join(
[f"{entry}" for col, entry in zip(result.keys(), item)]
)
@@ -111,45 +109,36 @@ class CustomDatabaseReader(BaseReader):
class DBLoaderConfig(BaseModel):
uri: str
queries: List[str]
queries: List[dict]
def get_db_documents(configs: list[DBLoaderConfig]):
def get_db_documents(configs: List[DBLoaderConfig]) -> List[Document]:
docs = []
if len(configs) == 0 or configs[0].uri == "":
if not configs or not configs[0].uri:
logger.warning(
f"Failed to load database, error message: uri is empty. Return as empty document list."
)
return docs
metadata = {
#'file_name':'',
'file_type':'application/booway.document.zj',
#'file_path':'',
#'file_size':'',
#'creation_date':'',
#'last_modified_date':'',
'file_type': 'application/booway.document.zj',
}
#from llama_index.readers.database import DatabaseReader
for entry in configs:
engine = create_engine(entry.uri)
sql_database = SQLDatabase(engine)
# table_schema_objs = makeDescriptionByEngine(sql_database)
# table_node_mapping = SQLTableNodeMapping(sql_database)
#
# nodes = table_node_mapping.to_nodes(table_schema_objs)
# for node in nodes:
# node.metadata.update(metadata)
#
# docs.extend(nodes)
queries = entry.queries or []
loader = CustomDatabaseReader(sql_database)
for query in queries:
for query_dict in entry.queries:
query = query_dict.get("sql", "")
explanation = query_dict.get("explanation", "")
logger.info(f"Loading data from database with query: {query}")
documents = loader.load_data(query=query)
docs.extend(documents)
# 添加解释到元数据中
for doc in documents:
doc.metadata["explanation"] = explanation
doc.metadata.update(metadata) # 更新或添加额外的元数据
docs.append(doc)
return docs
+117 -5
View File
@@ -6,6 +6,12 @@ from llama_index.core.readers.base import BaseReader
from llama_index.core.readers.json import JSONReader
from llama_parse import LlamaParse
from pydantic import BaseModel, validator
from app.engine.loaders.markdownReader import ChunkMarkdownReader
from app.engine.loaders.projectJson import ProjectJson
from typing import Any, Callable, Dict, Generator, List, Optional, Type, Set
import fsspec,mimetypes
from fsspec.implementations.local import LocalFileSystem
from datetime import datetime
logger = logging.getLogger(__name__)
@@ -20,6 +26,80 @@ class FileLoaderConfig(BaseModel):
raise ValueError(f"Directory '{v}' does not exist")
return v
class CustomFileMetadataFunc:
"""
Default file metadata function wrapper which stores the fs.
Allows for pickling of the function.
"""
def __init__(self, fs: Optional[fsspec.AbstractFileSystem] = None):
self.fs = fs or self._get_default_fs()
def __call__(self, file_path: str) -> Dict:
return self._default_file_metadata_func(file_path, self.fs)
def _default_file_metadata_func(self,
file_path: str, fs: Optional[fsspec.AbstractFileSystem] = None
) -> Dict:
"""
Get some handy metadata from filesystem.
Args:
file_path: str: file path in str
"""
fs = fs or self._get_default_fs()
stat_result = fs.stat(file_path)
try:
file_name = os.path.basename(str(stat_result["name"]))
except Exception as e:
file_name = os.path.basename(file_path)
creation_date = self._format_file_timestamp(stat_result.get("created"))
last_modified_date = self._format_file_timestamp(stat_result.get("mtime"))
last_accessed_date = self._format_file_timestamp(stat_result.get("atime"))
default_meta = {
"file_name": file_name,
"file_type": mimetypes.guess_type(file_path)[0],
"file_size": stat_result.get("size"),
"creation_date": creation_date,
"last_modified_date": last_modified_date,
"last_accessed_date": last_accessed_date,
}
# Return not null value
return {
meta_key: meta_value
for meta_key, meta_value in default_meta.items()
if meta_value is not None
}
def _format_file_timestamp(
timestamp: float, include_time: bool = False
) -> Optional[str]:
"""
Format file timestamp to a %Y-%m-%d string.
Args:
timestamp (float): timestamp in float
include_time (bool): whether to include time in the formatted string
Returns:
str: formatted timestamp
"""
try:
if include_time:
return datetime.utcfromtimestamp(timestamp).strftime("%Y-%m-%dT%H:%M:%SZ")
return datetime.fromtimestamp(timestamp).strftime("%Y-%m-%d")
except Exception:
return None
def _get_default_fs(self) -> fsspec.AbstractFileSystem:
return LocalFileSystem()
def _is_default_fs(self,fs: fsspec.AbstractFileSystem) -> bool:
return isinstance(fs, LocalFileSystem) and not fs.auto_mkdir
def llama_parse_parser():
if os.getenv("LLAMA_CLOUD_API_KEY") is None:
@@ -35,7 +115,6 @@ def llama_parse_parser():
)
return parser
def llama_parse_extractor() -> Dict[str, LlamaParse]:
from llama_parse.utils import SUPPORTED_FILE_TYPES
@@ -43,10 +122,13 @@ def llama_parse_extractor() -> Dict[str, LlamaParse]:
return {file_type: parser for file_type in SUPPORTED_FILE_TYPES}
def llama_local_extractor() -> Dict[str, BaseReader]:
return {".json" : JSONReader(clean_json=False,levels_back=0)}
parser = {
".json" : JSONReader(clean_json=False,levels_back=0),
".md" : ChunkMarkdownReader(),
}
return parser
def get_file_documents(config: FileLoaderConfig):
def get_file_documents(config: FileLoaderConfig,childPath: str):
from llama_index.core.readers import SimpleDirectoryReader
try:
@@ -63,11 +145,12 @@ def get_file_documents(config: FileLoaderConfig):
file_extractor = llama_local_extractor()
reader = SimpleDirectoryReader(
config.data_dir,
os.path.join(config.data_dir,childPath.replace('_','\\')),
recursive=True,
filename_as_id=True,
raise_on_error=True,
file_extractor=file_extractor,
file_metadata = CustomFileMetadataFunc()
)
return reader.load_data()
except Exception as e:
@@ -86,3 +169,32 @@ def get_file_documents(config: FileLoaderConfig):
else:
# Raise the error if it is not the case of empty data dir
raise e
def prjFileSuffix(dir:str):
entries = os.listdir(dir)
file_names = [entry for entry in entries if os.path.isfile(os.path.join(dir, entry))]
if len(file_names) > 0:
return os.path.splitext(file_names[0])[1]
return ''
def getProjectName(dir:str):
suffix = prjFileSuffix(dir)
if suffix== '.json':
prjJson = ProjectJson(dir)
prjJson.parse()
tb = prjJson.table('工程属性')
records = tb.records()
for record in records:
name = record.value('名称')
if name == '工程名称':
return record.value('')
elif suffix == '.md':
md_files = [f for f in os.listdir(dir) if f.endswith('.md')]
for md_file in md_files:
prjPath = os.path.join(dir, md_file)
basename = os.path.splitext(md_file)[0]
if basename =='工程属性':
rd = ChunkMarkdownReader()
rd.load_data(prjPath)
return rd.findValue("名称=='工程名称'",'')
return ''
+80
View File
@@ -0,0 +1,80 @@
from app.engine.loaders.projectJson import *
class MarkDown:
def __init__(self,table:JsonTable,path:str) -> None:
self._table = table
self._path = path
def build(self):
flds:Dict[str,Field] = self._table.fields()
records:List[Record] = self._table.records()
columns:list = []
colComments:list = []
ignores:List[str] = []
for name,fld in flds.items():
if self._table.name() == '工程属性' and (name =='_id' or name =='nodeType' or name =='relTbId'):
ignores.append(name)
continue
columns.append(fld.value('name'))
colComments.append(fld.value('alias'))
rowdatas = []
for record in records:
datas = []
for col in columns:
if col in ignores:
continue
txt:str = record.value(col)
content = txt.replace('\n',"")
content = content.replace('\r',"")
datas.append(content)
rowdatas.append(datas)
content = self.convert(self._table.name(),self._table.comment(),columns,colComments,rowdatas)
with open(self._path, 'w',encoding='utf-8') as file:
file.write(content)
def convert(self,tableName:str,tableComment:str,columns:list,colComments:list,rowdatas:list):
strTitle = "# " + tableName + '\n'
if tableName!='':
strTitle+= f"备注:{tableComment}" + '\n'
for i in range(len(columns)):
strTitle+= f"- 字段名称:{columns[i]}" + '\n'
comment = colComments[i]
if comment!='':
strTitle+= f" - 备注:{comment}" + '\n'
markdown_table = "|"
# 添加列标题
markdown_table += "|".join(columns) + "|\n"
# 添加分隔行
markdown_table += "|" + "|".join(['---' for _ in columns]) + "|\n"
# 遍历每个数据行
for row in rowdatas:
# 添加数据行
markdown_table += "|" + "|".join(row) + "|\n"
return strTitle + "\n" + markdown_table
if __name__ == "__main__":
intputDir = 'C:\\Users\\wanyaokun\\Desktop\\markdown\\Project'
outputDir = 'C:\\Users\\wanyaokun\\Desktop\\markdown\\data'
subdirectories = {}
for dp, dn, fn in os.walk(intputDir):
for d in dn:
subdirectories[d] = os.path.join(dp, d)
for dirName,dirPath in subdirectories.items():
prjSon = ProjectJson(dirPath)
prjSon.parse()
tables = prjSon.tables()
outPut = os.path.join(outputDir,dirName)
os.makedirs(outPut,exist_ok=True)
for name,table in tables.items():
outputPath = os.path.join(outPut,f'{table.name()}.md')
mdObj = MarkDown(table,outputPath)
mdObj.build()
@@ -0,0 +1,116 @@
from llama_index.readers.file.markdown import MarkdownReader
from typing import Any, Dict, List, Optional, Tuple
import re
from llama_index.core.utils import get_tokenizer
class ChunkMarkdownReader(MarkdownReader):
def __init__(
self,
*args: Any,
chunkSize:int = 2048,
**kwargs: Any,
) -> None:
self._chunkSize = chunkSize
self._tokenizer = get_tokenizer()
self._colheader = ''
self._rows = []
super().__init__(*args,**kwargs)
def markdown_to_tups(self, markdown_text: str) -> List[Tuple[Optional[str], str]]:
markdown_tups: List[Tuple[Optional[str], str]] = []
lines = self._multi_char_split(markdown_text,'\r\n')
lines = [line for line in lines if line!='']
strTitle = ''
tokensNum:int = 0
current_lines = []
strheader:str = ''
headerSize:int = 0
bAreadyJudgeTitle = False
for line in lines:
tokensNum += self._token_size(line)
if tokensNum > self._chunkSize and len(current_lines) > 0:
if len(markdown_tups) == 0:
titleHead = strTitle + '\n' + strheader if strTitle!= '' else strheader
markdown_tups.append((titleHead, "\n".join(current_lines)))
else:
markdown_tups.append((strheader , "\n".join(current_lines)))
tokensNum = headerSize
current_lines.clear()
if strheader!='':
self._rows.append(line)
if line.startswith('|') and strTitle == '' and not bAreadyJudgeTitle:
if len(current_lines) > 0:
if tokensNum > self._chunkSize:
raise ValueError('标题Token数大于chunkSize大小')
strTitle = "\n".join(current_lines)
current_lines.clear()
bAreadyJudgeTitle = True
current_lines.append(line)
if line.startswith("|---"):
self._colheader = current_lines[0]
strheader = "\n".join(current_lines)
headerSize= headerSize + self._token_size(strheader)
current_lines.clear()
if len(current_lines) > 0:
if len(markdown_tups) == 0:
titleHead = strTitle + '\n' + strheader if strTitle!= '' else strheader
markdown_tups.append((titleHead, "\n".join(current_lines)))
else:
markdown_tups.append((strheader , "\n".join(current_lines)))
return [
(
key if key is None else re.sub(r"#", "", key).strip(),
re.sub(r"<.*?>", "", value),
)
for key, value in markdown_tups
]
def _token_size(self, text: str) -> int:
return len(self._tokenizer(text))
def findValue(self,expression:str,Field:str):
cols = self._colheader.split('|')
cols = [item for item in cols if item]
for row in self._rows:
rowtrs = row.split('|')
rowdatas = [item for item in rowtrs if item and (item!='\r' or item!='\n')]
if len(rowdatas) == 0:
continue
gData = {}
for cName,rValue in zip(cols,rowdatas):
gData[cName] = rValue
if eval(expression,gData):
return gData[Field]
return ''
def records(self):
cols = self._colheader.split('|')
cols = cols[1:-1]
records = []
for row in self._rows:
rowtrs = row.split('|')
rowdatas = [item for item in rowtrs if (item!='\r' or item!='\n')]
rowdatas = rowdatas[1:-1]
if len(rowdatas) == 0:
continue
record = {}
for cName,rValue in zip(cols,rowdatas):
record[cName] = rValue
records.append(record)
return records
def _multi_char_split(self,string, separators):
# 将多个分隔符连成一个正则表达式
pattern = '[' + re.escape(separators) + ']'
# 使用正则表达式进行分割
return re.split(pattern, string)
+79
View File
@@ -0,0 +1,79 @@
from typing import Dict,List,Any
import json,os
class Record:
def __init__(self,datas:Dict[str,Any]) -> None:
self._datas:Dict[str,Any] = datas
def value(self,key:str):
if key in self._datas:
return self._datas.get(key)
return ''
class Field:
def __init__(self,datas:Dict[str,Any]) -> None:
self._datas:Dict[str,Any] = datas
def value(self,key:str):
if key in self._datas:
return self._datas.get(key)
return ''
class JsonTable:
def __init__(self,filePth:str) -> None:
self._filePth = filePth
self._fields:Dict[str,Field] = {}
self._records:List[Record] = []
self._fileName = os.path.splitext(os.path.basename(filePth))[0]
self._name = ''
self._comment = ''
def parse(self):
with open(self._filePth, 'r',encoding='utf-8') as file:
jsObj = json.load(file)
data:dict = jsObj.get('table')
self._name = data.get('name')
self._comment = data.get('comment')
Jsfields = data.get('fields')
for jsfiled in Jsfields:
field = Field(jsfiled)
self._fields[field.value('name')] =field
JsRecords = data.get('records')
for jsRecord in JsRecords:
self._records.append(Record(jsRecord))
def records(self):
return self._records
def fields(self):
return self._fields
def name(self):
return self._fileName
def comment(self):
return self._comment
class ProjectJson:
def __init__(self,dir:str) -> None:
self._dir = dir
self._tables:Dict[str,JsonTable] = {}
def parse(self):
json_files = [f for f in os.listdir(self._dir) if f.endswith('.json')]
for json_file in json_files:
prjPath = os.path.join(self._dir, json_file)
tb = JsonTable(prjPath)
tb.parse()
basename = os.path.splitext(json_file)[0]
self._tables[basename] = tb
def table(self,tableName:str):
return self._tables[tableName]
def tables(self):
return self._tables
@@ -0,0 +1,19 @@
from llama_index.llms.openai import OpenAI
from llama_index.core.base.llms.types import LLMMetadata
import os
class SiliconCloudOpenAI(OpenAI):
@property
def metadata(self) -> LLMMetadata:
bIsChat = os.getenv('IS_CHAT_MODEL')
bIsFuncall = os.getenv('IS_FUN_CALL_MODEL')
bIsChat = True if bIsChat.lower() in ['true','1'] else False
bIsFuncall = True if bIsFuncall.lower() in ['true','1'] else False
return LLMMetadata(
context_window= int(os.getenv('CONTEXT_WINDOW')),
num_output=self.max_tokens or -1,
is_chat_model=bIsChat,
is_function_calling_model=bIsFuncall,
model_name=self.model,
)
+123
View File
@@ -0,0 +1,123 @@
from llama_index.llms.xinference import Xinference
from typing import Any, Callable, Dict, Optional, Sequence, Tuple
from llama_index.core.llms.callbacks import (
llm_chat_callback,
llm_completion_callback,
)
from llama_index.core.base.llms.types import (
ChatMessage,
ChatResponse,
ChatResponseGen,
CompletionResponse,
CompletionResponseGen,
LLMMetadata,
MessageRole,
)
from llama_index.llms.xinference.utils import (
xinference_message_to_history,
xinference_modelname_to_contextsize,
)
class XinferenceModel(Xinference):
@llm_chat_callback()
def chat(self, messages: Sequence[ChatMessage], **kwargs: Any) -> ChatResponse:
msgs = []
assert self._generator is not None
for message in messages:
msgs.append(message.dict())
response_text = self._generator.chat(
messages=msgs,
generate_config={
"stream": False,
"temperature": self.temperature,
"max_tokens": self.max_tokens,
},
)["choices"][0]["message"]["content"]
return ChatResponse(
message=ChatMessage(
role=MessageRole.ASSISTANT,
content=response_text,
),
delta=None,
)
@llm_chat_callback()
def stream_chat(
self, messages: Sequence[ChatMessage], **kwargs: Any
) -> ChatResponseGen:
msgs = []
for message in messages:
msgs.append(message.dict())
assert self._generator is not None
response_iter = self._generator.chat(
messages=msgs,
generate_config={
"stream": True,
"temperature": self.temperature,
"max_tokens": self.max_tokens,
},
)
def gen() -> ChatResponseGen:
text = ""
for c in response_iter:
delta = c["choices"][0]["delta"].get("content", "")
text += delta
yield ChatResponse(
message=ChatMessage(
role=MessageRole.ASSISTANT,
content=text,
),
delta=delta,
)
return gen()
@llm_completion_callback()
def complete(
self, prompt: str, formatted: bool = False, **kwargs: Any
) -> CompletionResponse:
assert self._generator is not None
message = ChatMessage.from_str(prompt,MessageRole.SYSTEM)
msgs = [message.dict()]
response_text = self._generator.chat(
messages=msgs,
generate_config={
"stream": False,
"temperature": self.temperature,
"max_tokens": self.max_tokens,
},
)["choices"][0]["message"]["content"]
return CompletionResponse(
delta=None,
text=response_text,
)
@llm_completion_callback()
def stream_complete(
self, prompt: str, formatted: bool = False, **kwargs: Any
) -> CompletionResponseGen:
assert self._generator is not None
message = ChatMessage.from_str(prompt,MessageRole.SYSTEM)
msgs = [message.dict()]
response_iter = self._generator.chat(
messages=msgs,
generate_config={
"stream": True,
"temperature": self.temperature,
"max_tokens": self.max_tokens,
},
)
def gen() -> CompletionResponseGen:
text = ""
for c in response_iter:
delta = c["choices"][0]["delta"].get("content", "")
text += delta
yield CompletionResponse(
delta=delta,
text=text,
)
return gen()
+101 -57
View File
@@ -2,88 +2,132 @@ from llama_index.core import PromptTemplate
text_qa_template_str = (
"# 角色\n"
"你是一名博微造价工程数据查询助手,专精于电力工程文件中的信息。"
"你的职责是提供有关电力造价、造价编制软件、文件结构及相关数据的精准、客观的回答,"
"如同直接从文件中提取的内容。\n"
"## 技能\n"
"### 技能 1: 数据查询与提供\n"
"- 准确回答所有关于电力工程造价的相关问题。\n"
"- 提供具体数据,如成本估算、材料清单、劳动力需求等。\n"
"- 确保提供的信息严格基于工程文档中的记录\n"
"### 技能 2: 技术性解释\n"
"- 解释造价工程中的技术术语和概念\n"
"- 为复杂的工程细节提供清晰易懂的说明\n"
"## 约束\n"
"- 仅回答与电力工程造价文件相关的具体问题\n"
"- 不进行任何超出文件内容的猜测或假设。\n"
"- 所有回答均基于文件内容,采用客观和技术性的语言。\n"
"- 请基于这些信息回答问题。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。\n"
"以下为上下文信息\n"
"你是一名擅长博微造价工程数据问答的专家,可以根据电力工程文件中的内容回答用户问题。\n"
"\n"
"# 任务描述:\n"
"请仔细阅读所给的文档片段,并根据其内容回答问题。\n"
"您需要判断文档的内容是否可以回答问题,不要强行回答。如果可以回答,答案必须严格遵循文档内容,即使与事实不符。\n"
"如果答案与事实不符,直接给出答案,不要做解释。\n"
"\n"
"# 回答规则:\n"
"- 请使用与文档材料相同的语言回答问题\n"
"- 评估文档是否含有足够信息回答问题。无关时不要回答。\n"
"- 如果问题能被回答,你的回答必须严格遵循文档内容,即使与事实不符。一定不要做多余解释\n"
"- 如果问题能被回答,直接引用文档的相关信息保证答案准确、完整,并追求简洁\n"
"- 当文档中只有少量信息与问题相关时,重点关注这部分信息,这种情况下一定回答\n"
"- 当文档中信息与问题无关时,请不要额外发散回答,只需要回答“我不知道这个问题的答案”。\n"
"\n"
"来自多个来源的文档片段如下,请充分理解以下参考资料内容,组织出满足用户提问的条理清晰的回复\n"
"---------------------\n"
"{context_str}\n"
"---------------------\n"
"请根据上下文信息而非先知识回答我的问题或回复我的指令。前面的上下文信息可能有用,也可能没用,你需要从我给出的上下文信息中选出与我的问题最相关的那些,来为你的回答提供依据。回答一定要忠于原文,简洁但不丢信息,不要胡乱编造。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。我的问题或指令是什么语种,你就用什么语种回复\n"
"鉴于来自多个来源的文档片段而非先知识,回答查询\n"
"如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"问题:{query_str}\n"
"你的回复: "
"Query: {query_str}\n"
"Answer: "
)
text_qa_template = PromptTemplate(text_qa_template_str)
refine_template_str = (
"这是原本的问题: {query_str}\n"
"我们已经提供了回答: {existing_answer}\n"
"现在我们有机会改进这个回答 "
"使用以下更多上下文(仅当需要用时\n"
"使用以下更多上下文(仅当有助于改进回答时使用\n"
"你需要仔细的判断新的上下文的信息与原本问题必须一个字都不差,如果有一点差别,那就不能改变我现有的回答。\n"
"在判断回答是否正确的时候,你应该仔细对比新的上下文中包含的信息是否与原本的问题一字不差,如果一字不差,才能当作新的正确回答。\n"
"如果新的上下文对回答没有影响,或者原来的回答已经正确,不要在上次回答的后边再加上多余的补充信息,直接返回原本的回答。\n"
"判断一下如果原回答正确,且在新的上下文仍然包含正确的回答,请将新的回答与原回答一起返回。\n"
"------------\n"
"{context_msg}\n"
"------------\n"
"根据新的上下文, 请改进原来的回答。"
"如果新的上下文没有用, 直接返回原本的回答\n"
"如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"如果回答中已经包含有正确答案,不要返回多余的解释等信息,只返回正确答案\n"
"如果是表结构或者是数据库的相关内容,仅用于推导问题,不需要告诉用户数据库或表结构等物理信息\n"
"改进的回答: "
)
refine_template = PromptTemplate(refine_template_str)
summary_template_str = (
"# 角色\n"
"你是一名博微造价工程数据查询助手,专精于电力工程文件中的信息。"
"你的职责是提供有关电力造价、造价编制软件、文件结构及相关数据的精准、客观的回答,"
"如同直接从文件中提取的内容。\n"
# summary_template_str = (
# "# 角色\n"
# "你是一名擅长博微造价工程数据问答的专家,可以根据电力工程文件中的内容回答用户问题。\n"
# "\n"
# "# 任务描述:\n"
# "请仔细阅读所给的文档片段,并根据其内容回答问题。\n"
# "您需要判断文档的内容是否可以回答问题,不要强行回答。如果可以回答,答案必须严格遵循文档内容,即使与事实不符。\n"
# "如果答案与事实不符,直接给出答案,不要做解释。\n"
# "\n"
# "# 回答规则:\n"
# "- 请使用与文档材料相同的语言回答问题。\n"
# "- 评估文档是否含有足够信息回答问题。无关时不要回答。\n"
# "- 如果问题能被回答,你的回答必须严格遵循文档内容,即使与事实不符。一定不要做多余解释。\n"
# "- 如果问题能被回答,直接引用文档的相关信息保证答案准确、完整,并追求简洁。\n"
# "- 当文档中只有少量信息与问题相关时,重点关注这部分信息,这种情况下一定回答。\n"
# "- 当文档中信息与问题无关时,请不要额外发散回答,只需要回答为' '。\n"
# "\n"
# "来自多个来源的文档片段如下,请充分理解以下参考资料内容,组织出满足用户提问的条理清晰的回复。\n"
# "---------------------\n"
# "{context_str}\n"
# "---------------------\n"
# "鉴于来自多个来源的文档片段而非先验知识,回答查询。\n"
# "如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
# "Query: {query_str}\n"
# "Answer: "
# )
"## 技能\n"
"### 技能 1: 数据查询与提供\n"
"- 准确回答所有关于电力工程造价的相关问题。\n"
"- 提供具体数据,如成本估算、材料清单、劳动力需求等。\n"
"- 确保提供的信息严格基于工程文档中的记录。\n"
"### 技能 2: 技术性解释\n"
"- 解释造价工程中的技术术语和概念。\n"
"- 为复杂的工程细节提供清晰易懂的说明。\n"
summary_template_str = """
你是一名擅长博微造价工程数据问答的专家,可以根据电力工程文件中的内容回答用户问题。
来自多个来源的文档片段如下,请充分理解以下参考资料内容,回答问题。
---------------------
{context_str}
---------------------
当你不知道答案的时候,不要编造答案,直接回答不知道,不需要解释为什么不知道。
问题: {query_str}
回答:
"""
"## 约束\n"
"- 仅回答与电力工程造价文件相关的具体问题。\n"
"- 不进行任何超出文件内容的猜测或假设。\n"
"- 所有回答均基于文件内容,采用客观和技术性的语言。\n"
"- 请基于这些信息回答问题。如果无法找到相关信息,请不要额外发散回答,不要回答多余的信息,只需要回答“我不知道这个问题的答案”。\n"
"来自多个来源的上下文信息如下。\n"
"---------------------\n"
"{context_str}\n"
"---------------------\n"
"鉴于来自多个来源的信息而非先验知识, "
"回答查询。\n"
"如果是表结构或者是数据库的相关内容,只用于推导问题,不需要告诉用户数据库或表结构等物理信息。\n"
"Query: {query_str}\n"
"Answer: "
)
summary_template = PromptTemplate(summary_template_str)
simple_template_str = (
"{query_str}"
)
simple_template = PromptTemplate(simple_template_str)
ReActChatFormatter_messages = (
"您的设计旨在帮助完成各种任务,从回答问题到提供其他类型分析的摘要。\n\n"
"##工具\n\n"
"你可以访问各种工具。你有责任按照你认为合适的顺序使用这些工具来完成当前的任务。\n"
"这可能需要将任务分解为子任务,并使用不同的工具来完成每个子任务。\n\n"
"你可以访问以下工具:\n"
"{tool_desc}\n\n\n"
"##输出格式\n\n"
"请用与问题相同的语言回答,并使用以下格式:\n\n"
"'''\n"
"Thought: 用户当前的语言是:(user's language)。我需要使用工具来帮助我回答问题。\n"
"Action: 如果使用工具,则为工具名称(one of {tool_names})。\n"
"Action Input: 输入给工具的内容,使用JSON格式表示kwargs(例如{{\"input\": \"hello world\", \"num_beams\": 5}}\n"
"'''\n\n"
"请始终以Thought开始。\n\n"
"切勿用Markdown代码标记包围你的响应。如果需要,可以在响应中使用代码标记。\n\n"
"请为Action Input使用有效的JSON格式。不要这样做{{\'input\': \'hello world\', \'num_beams\': 5}}。\n\n"
"如果使用此格式,用户将以下面的格式进行回应:\n\n"
"'''\n"
"Observation: 工具响应\n"
"'''\n\n"
"你应该继续重复上述格式,直到你有足够的信息来回答问题而无需使用更多工具。此时,你必须使用以下两种格式之一进行回答:\n\n"
"'''\nThought: 我可以不用任何工具来回答。我将使用用户的语言来回答。\n"
"Answer: [你的答案(与用户问题相同的语言)]\n"
"'''\n\n"
"'''\n"
"Thought: 我无法使用提供的工具回答问题。\n"
"Answer: [你的答案(与用户问题相同的语言)]\n"
"'''\n\n##如果从工具中得到的回应是Empty Response,那么只需要回答“我不知道”,不需要额外回答别的内容。## 当前对话\n\n"
"以下是当前对话,由人类和助手的消息交替组成。\n"
)
summary_query_tool_messages = "适用于任何需要进行全面总结、概括的要求。"
query_engine_tool_messages = "适用于回答任何问题。"
tree_summary_query_engine_tool_messages = "在询问工程中单位的具体数值,例如用量,费率,合计,金额等的时候建议使用本工具。"
+70
View File
@@ -0,0 +1,70 @@
from typing import Any, List, Optional
from llama_index.core.postprocessor import SentenceTransformerRerank
from llama_index.core.schema import MetadataMode, NodeWithScore, QueryBundle
from llama_index.core.callbacks import CBEventType, EventPayload
from llama_index.core.bridge.pydantic import PrivateAttr
class OllamaRerank(SentenceTransformerRerank):
_score_threshold: float = PrivateAttr()
def __init__(
self,
top_n: int = 2,
model: str = "cross-encoder/stsb-distilroberta-base",
device: Optional[str] = None,
keep_retrieval_score: Optional[bool] = False,
score_threshold:float = 0.3
):
self._score_threshold = score_threshold
super().__init__(top_n,model,device,keep_retrieval_score)
@classmethod
def class_name(cls) -> str:
return "OllamaRerank"
def _postprocess_nodes(
self,
nodes: List[NodeWithScore],
query_bundle: Optional[QueryBundle] = None,
) -> List[NodeWithScore]:
if query_bundle is None:
raise ValueError("Missing query bundle in extra info.")
if len(nodes) == 0:
return []
query_and_nodes = [
(
query_bundle.query_str,
node.node.get_content(metadata_mode=MetadataMode.EMBED),
)
for node in nodes
]
with self.callback_manager.event(
CBEventType.RERANKING,
payload={
EventPayload.NODES: nodes,
EventPayload.MODEL_NAME: self.model,
EventPayload.QUERY_STR: query_bundle.query_str,
EventPayload.TOP_K: self.top_n,
},
) as event:
scores = self._model.predict(query_and_nodes)
assert len(scores) == len(nodes)
for node, score in zip(nodes, scores):
if self.keep_retrieval_score:
node.node.metadata["retrieval_score"] = node.score
node.score = score
for i in range(len(nodes)-1,-1,-1):
node = nodes[i]
if node.score < self._score_threshold:
nodes.remove(node)
new_nodes = sorted(nodes, key=lambda x: -x.score if x.score else 0)[
: self.top_n
]
event.on_end(payload={EventPayload.NODES: new_nodes})
return new_nodes
@@ -0,0 +1,97 @@
import requests
from typing import List, Optional
from llama_index.core.bridge.pydantic import Field
from llama_index.core.callbacks import CBEventType, EventPayload
from llama_index.core.instrumentation import get_dispatcher
from llama_index.core.instrumentation.events.rerank import (
ReRankEndEvent,
ReRankStartEvent,
)
from llama_index.core.postprocessor.types import BaseNodePostprocessor
from llama_index.core.schema import NodeWithScore, QueryBundle, MetadataMode
dispatcher = get_dispatcher(__name__)
class SiliconCloudRerank(BaseNodePostprocessor):
top_n: int = Field(
default=5,
description="The number of nodes to return.",
)
model: str = Field(
default="bge-reranker-base",
description="The SiliconCloud model uid to use.",
)
base_url: str = Field(
default="https://api.siliconflow.cn/v1",
description="The SiliconCloud base url to use.",
)
api_key:str = Field(
default="",
description="The SiliconCloud Api key to use.",
)
score_threshold: float = Field(default=0.3,description="分数阈值")
@classmethod
def class_name(cls) -> str:
return "SiliconCloudRerank"
def get_query_str(self, query):
return query.query_str if isinstance(query, QueryBundle) else query
def _postprocess_nodes(
self,
nodes: List[NodeWithScore],
query_bundle: Optional[QueryBundle] = None,
) -> List[NodeWithScore]:
dispatcher.event(
ReRankStartEvent(
query=query_bundle,
nodes=nodes,
top_n=self.top_n,
model_name=self.model,
)
)
if query_bundle is None:
raise ValueError("Missing query bundle.")
if len(nodes) == 0:
return []
with self.callback_manager.event(
CBEventType.RERANKING,
payload={
EventPayload.NODES: nodes,
EventPayload.MODEL_NAME: self.model,
EventPayload.QUERY_STR: self.get_query_str(query_bundle),
EventPayload.TOP_K: self.top_n,
},
) as event:
headers = {
"Content-Type": "application/json",
'Authorization': f'Bearer {self.api_key}'
}
json_data = {
"model": self.model,
"query": self.get_query_str(query_bundle),
"documents": [
node.node.get_content(metadata_mode=MetadataMode.EMBED)
for node in nodes
],
}
response = requests.post(
url=f"{self.base_url}/rerank", headers=headers, json=json_data
)
response.encoding = "utf-8"
if response.status_code != 200:
raise Exception(
f"SiliconCloud call failed with status code {response.status_code}."
f"Details: {response.text}"
)
rerank_nodes = [
NodeWithScore(
node=nodes[result["index"]].node, score=result["relevance_score"]
)
for result in response.json()["results"][: self.top_n]
]
event.on_end(payload={EventPayload.NODES: rerank_nodes})
dispatcher.event(ReRankEndEvent(nodes=rerank_nodes))
return rerank_nodes
@@ -0,0 +1,75 @@
import requests
from llama_index.postprocessor.xinference_rerank import XinferenceRerank
from llama_index.core.bridge.pydantic import Field
from typing import List, Optional
from llama_index.core.bridge.pydantic import Field
from llama_index.core.callbacks import CBEventType, EventPayload
from llama_index.core.instrumentation import get_dispatcher
from llama_index.core.instrumentation.events.rerank import (
ReRankEndEvent,
ReRankStartEvent,
)
from llama_index.core.schema import NodeWithScore, QueryBundle, MetadataMode
dispatcher = get_dispatcher(__name__)
class CustomXinFerenceRerank(XinferenceRerank):
score_threshold: float = Field(default=0.3,description="分数阈值")
def _postprocess_nodes(
self,
nodes: List[NodeWithScore],
query_bundle: Optional[QueryBundle] = None,
) -> List[NodeWithScore]:
dispatcher.event(
ReRankStartEvent(
query=query_bundle,
nodes=nodes,
top_n=self.top_n,
model_name=self.model,
)
)
if query_bundle is None:
raise ValueError("Missing query bundle.")
if len(nodes) == 0:
return []
with self.callback_manager.event(
CBEventType.RERANKING,
payload={
EventPayload.NODES: nodes,
EventPayload.MODEL_NAME: self.model,
EventPayload.QUERY_STR: self.get_query_str(query_bundle),
EventPayload.TOP_K: self.top_n,
},
) as event:
headers = {"Content-Type": "application/json"}
json_data = {
"model": self.model,
"query": self.get_query_str(query_bundle),
"documents": [
node.node.get_content(metadata_mode=MetadataMode.EMBED)
for node in nodes
],
}
response = requests.post(
url=f"{self.base_url}/v1/rerank", headers=headers, json=json_data
)
response.encoding = "utf-8"
if response.status_code != 200:
raise Exception(
f"Xinference call failed with status code {response.status_code}."
f"Details: {response.text}"
)
rerank_nodes = []
for result in response.json()["results"]:
node = NodeWithScore(
node=nodes[result["index"]].node, score=result["relevance_score"]
)
if node.score > self.score_threshold:
rerank_nodes.append(node)
if len(rerank_nodes) > self.top_n:
rerank_nodes = sorted(rerank_nodes,key=lambda x:x.score,reverse = True)[:self.top_n]
event.on_end(payload={EventPayload.NODES: rerank_nodes})
dispatcher.event(ReRankEndEvent(nodes=rerank_nodes))
return rerank_nodes
@@ -0,0 +1,234 @@
from llama_index.core.response_synthesizers.tree_summarize import TreeSummarize
from typing import Any, Optional, Sequence,List
import asyncio
from llama_index.core.callbacks.base import CallbackManager
from llama_index.core.indices.prompt_helper import PromptHelper
from llama_index.core.prompts import BasePromptTemplate
from llama_index.core.service_context import ServiceContext
from llama_index.core.llms import LLM
from llama_index.core.types import BaseModel,RESPONSE_TEXT_TYPE
from llama_index.core.async_utils import run_async_tasks
from llama_index.core.utils import get_tokenizer
from llama_index.core.prompts.prompt_utils import get_empty_prompt_txt
class CustomTreeResponse(TreeSummarize):
def __init__(
self,
llm: Optional[LLM] = None,
callback_manager: Optional[CallbackManager] = None,
prompt_helper: Optional[PromptHelper] = None,
summary_template: Optional[BasePromptTemplate] = None,
output_cls: Optional[BaseModel] = None,
streaming: bool = False,
use_async: bool = False,
verbose: bool = False,
service_context: Optional[ServiceContext] = None,
) -> None:
self._tokenizer = get_tokenizer()
super().__init__(llm,callback_manager,prompt_helper,summary_template,output_cls
,streaming,use_async,verbose,service_context)
async def aget_response(
self,
query_str: str,
text_chunks: Sequence[str],
**response_kwargs: Any,
) -> RESPONSE_TEXT_TYPE:
"""Get tree summarize response."""
summary_template = self._summary_template.partial_format(query_str=query_str)
text_chunks = self.repack(text_chunks=text_chunks)
if self._verbose:
print(f"{len(text_chunks)} text chunks after repacking")
# give final response if there is only one chunk
if len(text_chunks) == 1:
response: RESPONSE_TEXT_TYPE
if self._streaming:
response = await self._llm.astream(
summary_template, context_str=text_chunks[0], **response_kwargs
)
else:
if self._output_cls is None:
response = await self._llm.apredict(
summary_template,
context_str=text_chunks[0],
**response_kwargs,
)
else:
response = await self._llm.astructured_predict(
self._output_cls,
summary_template,
context_str=text_chunks[0],
**response_kwargs,
)
# return pydantic object if output_cls is specified
return response
else:
# summarize each chunk
if self._output_cls is None:
tasks = [
self._llm.apredict(
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
else:
tasks = [
self._llm.astructured_predict(
self._output_cls,
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
summary_responses = await asyncio.gather(*tasks)
if self._output_cls is not None:
summaries = [summary.json() for summary in summary_responses]
else:
summaries = summary_responses
# recursively summarize the summaries
return await self.aget_response(
query_str=query_str,
text_chunks=summaries,
**response_kwargs,
)
def get_response(
self,
query_str: str,
text_chunks: Sequence[str],
**response_kwargs: Any,
) -> RESPONSE_TEXT_TYPE:
"""Get tree summarize response."""
summary_template = self._summary_template.partial_format(query_str=query_str)
text_chunks = self.repack(text_chunks=text_chunks)
if self._verbose:
print(f"{len(text_chunks)} text chunks after repacking")
# give final response if there is only one chunk
if len(text_chunks) == 1:
response: RESPONSE_TEXT_TYPE
if self._streaming:
response = self._llm.stream(
summary_template, context_str=text_chunks[0], **response_kwargs
)
else:
if self._output_cls is None:
response = self._llm.predict(
summary_template,
context_str=text_chunks[0],
**response_kwargs,
)
else:
response = self._llm.structured_predict(
self._output_cls,
summary_template,
context_str=text_chunks[0],
**response_kwargs,
)
return response
else:
# summarize each chunk
if self._use_async:
if self._output_cls is None:
tasks = [
self._llm.apredict(
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
else:
tasks = [
self._llm.astructured_predict(
self._output_cls,
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
summary_responses = run_async_tasks(tasks)
if self._output_cls is not None:
summaries = [summary.json() for summary in summary_responses]
else:
summaries = summary_responses
else:
if self._output_cls is None:
summaries = [
self._llm.predict(
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
else:
summaries = [
self._llm.structured_predict(
self._output_cls,
summary_template,
context_str=text_chunk,
**response_kwargs,
)
for text_chunk in text_chunks
]
summaries = [summary.json() for summary in summaries]
# recursively summarize the summaries
return self.get_response(
query_str=query_str, text_chunks=summaries, **response_kwargs
)
def repack( self,text_chunks: Sequence[str],) ->List[str]:
prompt_str = get_empty_prompt_txt(self._summary_template)
num_prompt_tokens = self._token_size(prompt_str)
avaliableSize = self._get_available_context_size(num_prompt_tokens)
ava_chunks = []
sumSize = 0
results = []
for text_chunk in text_chunks:
one_chunk_size = self._token_size(text_chunk)
if one_chunk_size > avaliableSize:
raise ValueError("文本块大小大于可用上下文大小")
sumSize = sumSize + one_chunk_size
if sumSize > avaliableSize:
results.append(self._merge_chunks(ava_chunks))
ava_chunks.clear()
sumSize = 0
ava_chunks.append(text_chunk)
if len(ava_chunks) > 0:
results.append(self._merge_chunks(ava_chunks))
return results
def _get_available_context_size(self, num_prompt_tokens: int) -> int:
llm_metadata = self._llm.metadata
context_size_tokens = llm_metadata.context_window - num_prompt_tokens - llm_metadata.num_output
if context_size_tokens < 0:
raise ValueError(
f"Calculated available context size {context_size_tokens} was"
" not non-negative."
)
return context_size_tokens
def _token_size(self, text: str) -> int:
return len(self._tokenizer(text))
def _merge_chunks(self,ava_chunks:list):
return "\n\n".join([c.strip() for c in ava_chunks if c.strip()])
@@ -1,133 +0,0 @@
import json
import logging
import os
from typing import Any, Callable, Dict, List, Optional, cast
from llama_index.core.base.base_retriever import BaseRetriever
from llama_index.core.callbacks.base import CallbackManager
from llama_index.core.constants import DEFAULT_SIMILARITY_TOP_K
from llama_index.core.indices.vector_store.base import VectorStoreIndex
from llama_index.core.schema import BaseNode, IndexNode, NodeWithScore, QueryBundle
from llama_index.core.storage.docstore.types import BaseDocumentStore
from llama_index.core.vector_stores.utils import (
node_to_metadata_dict,
metadata_dict_to_node,
)
import bm25s
from app.engine.retriever.CHTokener import chTokenize
CHDEFAULT_PERSIST_ARGS = {"similarity_top_k": "similarity_top_k", "_verbose": "verbose"}
CHDEFAULT_PERSIST_FILENAME = "retriever.json"
class CHBM25Retriever(BaseRetriever):
def __init__(
self,
nodes: Optional[List[BaseNode]] = None,
existing_bm25: Optional[bm25s.BM25] = None,
similarity_top_k: int = DEFAULT_SIMILARITY_TOP_K,
callback_manager: Optional[CallbackManager] = None,
objects: Optional[List[IndexNode]] = None,
object_map: Optional[dict] = None,
verbose: bool = False,
) -> None:
self.similarity_top_k = similarity_top_k
if existing_bm25 is not None:
self.bm25 = existing_bm25
self.corpus = existing_bm25.corpus
else:
from nltk.corpus import stopwords
if nodes is None:
raise ValueError("Please pass nodes or an existing BM25 object.")
self.corpus = [node_to_metadata_dict(node) for node in nodes]
corpus_tokens = chTokenize(
[node.get_content() for node in nodes],
show_progress=verbose,
)
self.bm25 = bm25s.BM25()
self.bm25.index(corpus_tokens, show_progress=verbose)
super().__init__(
callback_manager=callback_manager,
object_map=object_map,
objects=objects,
verbose=verbose,
)
@classmethod
def from_defaults(
cls,
index: Optional[VectorStoreIndex] = None,
nodes: Optional[List[BaseNode]] = None,
docstore: Optional[BaseDocumentStore] = None,
similarity_top_k: int = DEFAULT_SIMILARITY_TOP_K,
verbose: bool = False,
) -> "CHBM25Retriever":
if sum(bool(val) for val in [index, nodes, docstore]) != 1:
raise ValueError("Please pass exactly one of index, nodes, or docstore.")
if index is not None:
docstore = index.docstore
if docstore is not None:
nodes = cast(List[BaseNode], list(docstore.docs.values()))
assert (
nodes is not None
), "Please pass exactly one of index, nodes, or docstore."
return cls(
nodes=nodes,
similarity_top_k=similarity_top_k,
verbose=verbose,
)
def get_persist_args(self) -> Dict[str, Any]:
"""Get Persist Args Dict to Save."""
return {
CHDEFAULT_PERSIST_ARGS[key]: getattr(self, key)
for key in CHDEFAULT_PERSIST_ARGS
if hasattr(self, key)
}
def persist(self, path: str, **kwargs: Any) -> None:
"""Persist the retriever to a directory."""
self.bm25.save(path, corpus=self.corpus, **kwargs)
with open(os.path.join(path, CHDEFAULT_PERSIST_FILENAME), "w") as f:
json.dump(self.get_persist_args(), f, indent=2)
@classmethod
def from_persist_dir(cls, path: str, **kwargs: Any) -> "CHBM25Retriever":
"""Load the retriever from a directory."""
bm25 = bm25s.BM25.load(path, load_corpus=True, **kwargs)
with open(os.path.join(path, CHDEFAULT_PERSIST_FILENAME)) as f:
retriever_data = json.load(f)
return cls(existing_bm25=bm25, **retriever_data)
def _retrieve(self, query_bundle: QueryBundle) -> List[NodeWithScore]:
query = query_bundle.query_str
tokenized_query = chTokenize(
query,show_progress=self._verbose
)
indexes, scores = self.bm25.retrieve(
tokenized_query, k=self.similarity_top_k, show_progress=self._verbose
)
# batched, but only one query
indexes = indexes[0]
scores = scores[0]
nodes: List[NodeWithScore] = []
for idx, score in zip(indexes, scores):
# idx can be an int or a dict of the node
if isinstance(idx, dict):
node = metadata_dict_to_node(idx)
else:
node_dict = self.corpus[int(idx)]
node = metadata_dict_to_node(node_dict)
nodes.append(NodeWithScore(node=node, score=float(score)))
return nodes
@@ -1,46 +0,0 @@
from typing import Any, Dict, List, Union, Callable, NamedTuple
from bm25s.tokenization import *
try:
from tqdm.auto import tqdm
except ImportError:
def tqdm(iterable, *args, **kwargs):
return iterable
def chinese_tokenizer(text: str) -> List[str]:
import jieba
from nltk.corpus import stopwords
tokens = jieba.lcut(text)
return [token for token in tokens if token not in stopwords.words('chinese')]
def chTokenize(
texts,
show_progress: bool = True,
leave: bool = False,
) -> Union[List[List[str]], Tokenized]:
if isinstance(texts, str):
texts = [texts]
corpus_ids = []
token_to_index = {}
for text in tqdm(
texts, desc="Split strings", leave=leave, disable=not show_progress
):
splitted = chinese_tokenizer(text)
doc_ids = []
for token in splitted:
if token not in token_to_index:
token_to_index[token] = len(token_to_index)
token_id = token_to_index[token]
doc_ids.append(token_id)
corpus_ids.append(doc_ids)
return Tokenized(ids=corpus_ids, vocab=token_to_index)
@@ -1,67 +0,0 @@
import os
from typing import Optional, Any, Dict, List
from llama_index.core.base.base_retriever import BaseRetriever
from llama_index.core.schema import NodeWithScore, QueryBundle
from app.engine.retriever.CHBM25Retriever import CHBM25Retriever
class HybridRetriever(BaseRetriever):
def __init__(
self,
vector_index,
similarity_top_k: int = 2,
out_top_k: Optional[int] = None,
alpha: float = 0.5,
filters = None,
**kwargs: Any,
) -> None:
super().__init__(**kwargs)
self._vector_index = vector_index
self._embed_model = vector_index._embed_model
self._out_top_k = out_top_k or similarity_top_k
self._vecRetriever = vector_index.as_retriever(
similarity_top_k=similarity_top_k,filters = filters
)
STORAGE_DIR = os.getenv("BM_RETRIEVER_PATH", "storage_bm")
if os.path.exists(STORAGE_DIR) and len(os.listdir(STORAGE_DIR)) > 0:
self._bm25Retriever = CHBM25Retriever.from_persist_dir(STORAGE_DIR)
else:
bmRetriver = CHBM25Retriever.from_defaults(similarity_top_k=similarity_top_k,nodes=self._vector_index.vector_store.get_nodes(None))
bmRetriver.persist(STORAGE_DIR)
self._alpha = alpha
def _retrieve(self, query_bundle: QueryBundle) -> List[NodeWithScore]:
vecNodes:List[NodeWithScore] = self._vecRetriever.retrieve(query_bundle.query_str)
bmNodes:List[NodeWithScore] = self._bm25Retriever.retrieve(query_bundle.query_str)
bmDic:Dict[str,NodeWithScore] = {}
for node in bmNodes:
bmDic[node.node_id] = node
result_tups = []
for i in range(len(vecNodes)):
node = vecNodes[i]
bmScore = 0.0
if node.node_id in bmDic:
bmScore = bmDic[node.node_id].score
bmDic.pop(node.node_id)
else:
bmScore = 0.0
full_similarity = (self._alpha * node.score) + (
(1 - self._alpha) * bmScore
)
result_tups.append((full_similarity, node))
for _,node in bmDic.items():
full_similarity = (1 - self._alpha) * node.score
result_tups.append((full_similarity, node))
result_tups = sorted(result_tups, key=lambda x: x[0], reverse=True)
for full_score, node in result_tups:
node.score = full_score
return [n for _, n in result_tups][:self._out_top_k]
+5 -1
View File
@@ -1,3 +1,4 @@
import os
from typing import Any, Dict, List, Union, Callable, NamedTuple
from bm25s.tokenization import *
@@ -8,9 +9,12 @@ except ImportError:
def tqdm(iterable, *args, **kwargs):
return iterable
import jieba
jiebapath = os.environ.get("JIEBA_DATA", "")
jieba.set_dictionary(os.path.join(jiebapath, 'dict.txt')) #设置字典
jieba.initialize() #初始化jeiba
def chinese_tokenizer(text: str) -> List[str]:
import jieba
from nltk.corpus import stopwords
tokens = jieba.lcut(text)
return [token for token in tokens if token not in stopwords.words('chinese')]
@@ -24,13 +24,15 @@ class HybridRetriever(BaseRetriever):
self._vecRetriever = vector_index.as_retriever(
similarity_top_k=similarity_top_k,filters = filters
)
self._bm25Retriever = None
STORAGE_DIR = os.getenv("BM_RETRIEVER_PATH", "storage_bm")
if os.path.exists(STORAGE_DIR) and len(os.listdir(STORAGE_DIR)) > 0:
self._bm25Retriever = CHBM25Retriever.from_persist_dir(STORAGE_DIR)
else:
bmRetriver = CHBM25Retriever.from_defaults(similarity_top_k=similarity_top_k,nodes=self._vector_index.vector_store.get_nodes(None))
bmRetriver.persist(STORAGE_DIR)
nodes = self._vector_index.vector_store.get_nodes(None)
similarity_top_k = min(len(nodes),similarity_top_k)
self._bm25Retriever = CHBM25Retriever.from_defaults(similarity_top_k=similarity_top_k,nodes=nodes)
self._bm25Retriever.persist(STORAGE_DIR)
self._alpha = alpha
@@ -43,6 +45,16 @@ class HybridRetriever(BaseRetriever):
for node in bmNodes:
bmDic[node.node_id] = node
vecScores = [node_with_score.score for node_with_score in vecNodes]
bmSores = [node_with_score.score for node_with_score in bmNodes]
vec_min_score = min(vecScores) if len(vecScores) > 0 else 0
vec_max_score = max(vecScores) if len(vecScores) > 0 else 0
bm_min_score = min(bmSores) if len(bmSores) > 0 else 0
bm_max_score = max(bmSores) if len(bmSores) > 0 else 0
result_tups = []
for i in range(len(vecNodes)):
node = vecNodes[i]
@@ -52,7 +64,11 @@ class HybridRetriever(BaseRetriever):
bmDic.pop(node.node_id)
else:
bmScore = 0.0
full_similarity = (self._alpha * node.score) + (
bmScore = self.normal_score(bmScore,bm_min_score,bm_max_score)
vecScore = self.normal_score(node.score,vec_min_score,vec_max_score)
full_similarity = (self._alpha * vecScore) + (
(1 - self._alpha) * bmScore
)
result_tups.append((full_similarity, node))
@@ -65,3 +81,9 @@ class HybridRetriever(BaseRetriever):
for full_score, node in result_tups:
node.score = full_score
return [n for _, n in result_tups][:self._out_top_k]
def normal_score(self,score,min,max):
if min == max:
return 1.0 if score > 0 else 0.0
else:
return (score - min) / (max - min)
@@ -0,0 +1,73 @@
import os
from typing import Any, List, Sequence, Optional
from llama_index.core.schema import BaseNode, NodeWithScore, QueryBundle
from llama_index.core.graph_stores.types import (
PropertyGraphStore,
KG_SOURCE_REL,
VECTOR_SOURCE_KEY,
)
from llama_index.core.indices.property_graph.sub_retrievers.base import BasePGRetriever
from llama_index.core.graph_stores.types import (
PropertyGraphStore,
KG_SOURCE_REL
)
from app.engine.retriever.CHBM25Retriever import CHBM25Retriever
class GraphBM25Retriever(BasePGRetriever):
def __init__(
self,
graph_store: PropertyGraphStore,
include_text: bool = True,
path_depth: int = 1,
similarity_score: Optional[float] = None,
**kwargs: Any,
) -> None:
self._path_depth = path_depth
self._similarity_score = similarity_score
STORAGE_DIR = os.getenv("BM_RETRIEVER_PATH", "storage_bm")
if os.path.exists(STORAGE_DIR) and len(os.listdir(STORAGE_DIR)) > 0:
self._bm25Retriever = CHBM25Retriever.from_persist_dir(STORAGE_DIR)
super().__init__(graph_store=graph_store, include_text=include_text, **kwargs)
async def aretrieve_from_graph(
self, query_bundle: QueryBundle
) -> List[NodeWithScore]:
query_result:List[NodeWithScore] = self._bm25Retriever._retrieve(query_bundle.query_str)
nodes,scores = [],[]
for scoreNode in query_result:
nodes.append(scoreNode.node)
scores.append(scoreNode.score)
kg_ids = self._get_kg_ids(nodes)
kg_nodes = await self._graph_store.aget(ids=kg_ids)
triplets = await self._graph_store.aget_rel_map(
kg_nodes, depth=self._path_depth, ignore_rels=[KG_SOURCE_REL]
)
new_scores = []
for triplet in triplets:
score1 = (
scores[kg_ids.index(triplet[0].id)] if triplet[0].id in kg_ids else 0.0
)
score2 = (
scores[kg_ids.index(triplet[2].id)] if triplet[2].id in kg_ids else 0.0
)
new_scores.append(max(score1, score2))
assert len(triplets) == len(new_scores)
if self._similarity_score:
filtered_data = [
(triplet, score)
for triplet, score in zip(triplets, new_scores)
if score >= self._similarity_score
]
top_k = sorted(filtered_data, key=lambda x: x[1], reverse=True)
else:
top_k = sorted(zip(triplets, new_scores), key=lambda x: x[1], reverse=True)
return self._get_nodes_with_score([x[0] for x in top_k], [x[1] for x in top_k])
def _get_kg_ids(self, kg_nodes: Sequence[BaseNode]) -> List[str]:
"""Backward compatibility method to get kg_ids from kg_nodes."""
return [node.metadata.get(VECTOR_SOURCE_KEY, node.id_) for node in kg_nodes]
@@ -0,0 +1,63 @@
from typing import Any, Callable, List, Optional, Union
from llama_index.core.llms.llm import LLM
from llama_index.core.indices.property_graph.sub_retrievers.base import (
BasePGRetriever,
)
from llama_index.core.graph_stores.types import (
PropertyGraphStore,
KG_SOURCE_REL,
)
from llama_index.core.settings import Settings
from llama_index.core.schema import (
NodeWithScore,
QueryBundle,
)
from llama_index.core.graph_stores.types import EntityNode
class GraphKeyWordRetriever(BasePGRetriever):
def __init__(
self,
graph_store: PropertyGraphStore,
include_text: bool = True,
path_depth: int = 1,
llm: Optional[LLM] = None,
**kwargs: Any,
) -> None:
self._llm = llm or Settings.llm
self._path_depth = path_depth
super().__init__(graph_store=graph_store, include_text=include_text, **kwargs)
def _prepare_matches(self,query_bundle: QueryBundle) -> List[NodeWithScore]:
kg_nodes = []
labelNodes = self._graph_store.get()
for labelNode in labelNodes:
if isinstance(labelNode,EntityNode) and labelNode.name in query_bundle.query_str:
kg_nodes.append(labelNode)
triplets = self._graph_store.get_rel_map(
kg_nodes,
depth=self._path_depth,
ignore_rels=[KG_SOURCE_REL],
)
return self._get_nodes_with_score(triplets)
async def _aprepare_matches(self,query_bundle: QueryBundle) -> List[NodeWithScore]:
kg_nodes = []
labelNodes = await self._graph_store.aget()
for labelNode in labelNodes:
if isinstance(labelNode,EntityNode) and labelNode.name in query_bundle.query_str:
kg_nodes.append(labelNode)
triplets = await self._graph_store.aget_rel_map(
kg_nodes,
depth=self._path_depth,
ignore_rels=[KG_SOURCE_REL],
)
return self._get_nodes_with_score(triplets)
def retrieve_from_graph(self, query_bundle: QueryBundle) -> List[NodeWithScore]:
return self._prepare_matches(query_bundle)
async def aretrieve_from_graph(
self, query_bundle: QueryBundle
) -> List[NodeWithScore]:
return await self._aprepare_matches(query_bundle)
@@ -1,36 +0,0 @@
from llama_index.core.tools.function_tool import FunctionTool
def duckduckgo_search(
query: str,
region: str = "wt-wt",
max_results: int = 10,
):
"""
Use this function to search for any query in DuckDuckGo.
Args:
query (str): The query to search in DuckDuckGo.
region Optional(str): The region to be used for the search in [country-language] convention, ex us-en, uk-en, ru-ru, etc...
max_results Optional(int): The maximum number of results to be returned. Default is 10.
"""
try:
from duckduckgo_search import DDGS
except ImportError:
raise ImportError(
"duckduckgo_search package is required to use this function."
"Please install it by running: `poetry add duckduckgo_search` or `pip install duckduckgo_search`"
)
params = {
"keywords": query,
"region": region,
"max_results": max_results,
}
results = []
with DDGS() as ddg:
results = list(ddg.text(**params))
return results
def get_tools(**kwargs):
return [FunctionTool.from_defaults(duckduckgo_search)]
@@ -1,60 +0,0 @@
import os
import yaml
import json
import importlib
from cachetools import cached, LRUCache
from llama_index.core.tools.tool_spec.base import BaseToolSpec
from llama_index.core.tools.function_tool import FunctionTool
class ToolType:
LLAMAHUB = "llamahub"
LOCAL = "local"
class ToolFactory:
TOOL_SOURCE_PACKAGE_MAP = {
ToolType.LLAMAHUB: "llama_index.tools",
ToolType.LOCAL: "app.engine.tools",
}
def load_tools(tool_type: str, tool_name: str, config: dict) -> list[FunctionTool]:
source_package = ToolFactory.TOOL_SOURCE_PACKAGE_MAP[tool_type]
try:
if "ToolSpec" in tool_name:
tool_package, tool_cls_name = tool_name.split(".")
module_name = f"{source_package}.{tool_package}"
module = importlib.import_module(module_name)
tool_class = getattr(module, tool_cls_name)
tool_spec: BaseToolSpec = tool_class(**config)
return tool_spec.to_tool_list()
else:
module = importlib.import_module(f"{source_package}.{tool_name}")
tools = module.get_tools(**config)
if not all(isinstance(tool, FunctionTool) for tool in tools):
raise ValueError(
f"The module {module} does not contain valid tools"
)
return tools
except ImportError as e:
raise ValueError(f"Failed to import tool {tool_name}: {e}")
except AttributeError as e:
raise ValueError(f"Failed to load tool {tool_name}: {e}")
@staticmethod
def from_env() -> list[FunctionTool]:
tools = []
if os.path.exists("config/tools.yaml"):
with open("config/tools.yaml", "r") as f:
tool_configs = yaml.safe_load(f)
if tool_configs != None and len(tool_configs.items()) != 0:
for tool_type, config_entries in tool_configs.items():
if config_entries == None or len(config_entries.items()) == 0:
continue
for tool_name, config in config_entries.items():
tools.extend(
ToolFactory.load_tools(tool_type, tool_name, config)
)
return tools
@@ -1,108 +0,0 @@
import os
import uuid
import logging
import requests
from typing import Optional
from pydantic import BaseModel, Field
from llama_index.core.tools import FunctionTool
logger = logging.getLogger(__name__)
class ImageGeneratorToolOutput(BaseModel):
is_success: bool = Field(
...,
description="Whether the image generation was successful.",
)
image_url: Optional[str] = Field(
None,
description="The URL of the generated image.",
)
error_message: Optional[str] = Field(
None,
description="The error message if the image generation failed.",
)
class ImageGeneratorTool:
_IMG_OUTPUT_FORMAT = "webp"
_IMG_OUTPUT_DIR = "output/tool"
_IMG_GEN_API = "https://api.stability.ai/v2beta/stable-image/generate/core"
def __init__(self, api_key: str = None):
if not api_key:
api_key = os.getenv("STABILITY_API_KEY")
self._api_key = api_key
self.fileserver_url_prefix = os.getenv("FILESERVER_URL_PREFIX")
if self._api_key is None:
raise ValueError(
"STABILITY_API_KEY key is required to run image generator. Get it here: https://platform.stability.ai/account/keys"
)
if self.fileserver_url_prefix is None:
raise ValueError("FILESERVER_URL_PREFIX is required.")
def _prepare_output_dir(self):
"""
Create the output directory if it doesn't exist
"""
if not os.path.exists(self._IMG_OUTPUT_DIR):
os.makedirs(self._IMG_OUTPUT_DIR, exist_ok=True)
def _save_image(self, image_data: bytes):
self._prepare_output_dir()
filename = f"{uuid.uuid4()}.{self._IMG_OUTPUT_FORMAT}"
output_path = os.path.join(self._IMG_OUTPUT_DIR, filename)
with open(output_path, "wb") as f:
f.write(image_data)
url = f"{os.getenv('FILESERVER_URL_PREFIX')}/{self._IMG_OUTPUT_DIR}/{filename}"
logger.info(f"Saved image to {output_path}.\nURL: {url}")
return url
def _call_stability_api(self, prompt: str):
headers = {
"authorization": f"Bearer {self._api_key}",
"accept": "image/*",
}
data = {
"prompt": prompt,
"output_format": self._IMG_OUTPUT_FORMAT,
}
response = requests.post(
self._IMG_GEN_API,
headers=headers,
files={"none": ""},
data=data,
)
response.raise_for_status()
return response
def generate_image(self, prompt: str) -> ImageGeneratorToolOutput:
"""
Use this tool to generate an image based on the prompt.
Args:
prompt (str): The prompt to generate the image from.
"""
try:
# Call the Stability API
response = self._call_stability_api(prompt)
# Save the image and get the URL
image_url = self._save_image(response.content)
return ImageGeneratorToolOutput(
is_success=True,
image_url=image_url,
)
except Exception as e:
logger.exception(e, exc_info=True)
return ImageGeneratorToolOutput(
is_success=False,
error_message=str(e),
)
def get_tools(**kwargs):
return [FunctionTool.from_defaults(ImageGeneratorTool(**kwargs).generate_image)]
@@ -1,143 +0,0 @@
import os
import logging
import base64
import uuid
from pydantic import BaseModel
from typing import List, Tuple, Dict, Optional
from llama_index.core.tools import FunctionTool
from e2b_code_interpreter import CodeInterpreter
from e2b_code_interpreter.models import Logs
logger = logging.getLogger(__name__)
class InterpreterExtraResult(BaseModel):
type: str
content: Optional[str] = None
filename: Optional[str] = None
url: Optional[str] = None
class E2BToolOutput(BaseModel):
is_error: bool
logs: Logs
results: List[InterpreterExtraResult] = []
class E2BCodeInterpreter:
output_dir = "output/tool"
def __init__(self, api_key: str = None):
if api_key is None:
api_key = os.getenv("E2B_API_KEY")
filesever_url_prefix = os.getenv("FILESERVER_URL_PREFIX")
if not api_key:
raise ValueError(
"E2B_API_KEY key is required to run code interpreter. Get it here: https://e2b.dev/docs/getting-started/api-key"
)
if not filesever_url_prefix:
raise ValueError(
"FILESERVER_URL_PREFIX is required to display file output from sandbox"
)
self.filesever_url_prefix = filesever_url_prefix
self.interpreter = CodeInterpreter(api_key=api_key)
def __del__(self):
self.interpreter.close()
def get_output_path(self, filename: str) -> str:
# if output directory doesn't exist, create it
if not os.path.exists(self.output_dir):
os.makedirs(self.output_dir, exist_ok=True)
return os.path.join(self.output_dir, filename)
def save_to_disk(self, base64_data: str, ext: str) -> Dict:
filename = f"{uuid.uuid4()}.{ext}" # generate a unique filename
buffer = base64.b64decode(base64_data)
output_path = self.get_output_path(filename)
try:
with open(output_path, "wb") as file:
file.write(buffer)
except IOError as e:
logger.error(f"Failed to write to file {output_path}: {str(e)}")
raise e
logger.info(f"Saved file to {output_path}")
return {
"outputPath": output_path,
"filename": filename,
}
def get_file_url(self, filename: str) -> str:
return f"{self.filesever_url_prefix}/{self.output_dir}/{filename}"
def parse_result(self, result) -> List[InterpreterExtraResult]:
"""
The result could include multiple formats (e.g. png, svg, etc.) but encoded in base64
We save each result to disk and return saved file metadata (extension, filename, url)
"""
if not result:
return []
output = []
try:
formats = result.formats()
results = [result[format] for format in formats]
for ext, data in zip(formats, results):
match ext:
case "png" | "svg" | "jpeg" | "pdf":
result = self.save_to_disk(data, ext)
filename = result["filename"]
output.append(
InterpreterExtraResult(
type=ext,
filename=filename,
url=self.get_file_url(filename),
)
)
case _:
output.append(
InterpreterExtraResult(
type=ext,
content=data,
)
)
except Exception as error:
logger.exception(error, exc_info=True)
logger.error("Error when parsing output from E2b interpreter tool", error)
return output
def interpret(self, code: str) -> E2BToolOutput:
"""
Execute python code in a Jupyter notebook cell, the toll will return result, stdout, stderr, display_data, and error.
Parameters:
code (str): The python code to be executed in a single cell.
"""
logger.info(
f"\n{'='*50}\n> Running following AI-generated code:\n{code}\n{'='*50}"
)
exec = self.interpreter.notebook.exec_cell(code)
if exec.error:
logger.error("Error when executing code", exec.error)
output = E2BToolOutput(is_error=True, logs=exec.logs, results=[])
else:
if len(exec.results) == 0:
output = E2BToolOutput(is_error=False, logs=exec.logs, results=[])
else:
results = self.parse_result(exec.results[0])
output = E2BToolOutput(is_error=False, logs=exec.logs, results=results)
return output
def get_tools(**kwargs):
return [FunctionTool.from_defaults(E2BCodeInterpreter(**kwargs).interpret)]
@@ -1,78 +0,0 @@
from typing import Dict, List, Tuple
from llama_index.tools.openapi import OpenAPIToolSpec
from llama_index.tools.requests import RequestsToolSpec
class OpenAPIActionToolSpec(OpenAPIToolSpec, RequestsToolSpec):
"""
A combination of OpenAPI and Requests tool specs that can parse OpenAPI specs and make requests.
openapi_uri: str: The file path or URL to the OpenAPI spec.
domain_headers: dict: Whitelist domains and the headers to use.
"""
spec_functions = OpenAPIToolSpec.spec_functions + RequestsToolSpec.spec_functions
# Cached parsed specs by URI
_specs: Dict[str, Tuple[Dict, List[str]]] = {}
def __init__(self, openapi_uri: str, domain_headers: dict = None, **kwargs):
if domain_headers is None:
domain_headers = {}
if openapi_uri not in self._specs:
openapi_spec, servers = self._load_openapi_spec(openapi_uri)
self._specs[openapi_uri] = (openapi_spec, servers)
else:
openapi_spec, servers = self._specs[openapi_uri]
# Add the servers to the domain headers if they are not already present
for server in servers:
if server not in domain_headers:
domain_headers[server] = {}
OpenAPIToolSpec.__init__(self, spec=openapi_spec)
RequestsToolSpec.__init__(self, domain_headers)
@staticmethod
def _load_openapi_spec(uri: str) -> Tuple[Dict, List[str]]:
"""
Load an OpenAPI spec from a URI.
Args:
uri (str): A file path or URL to the OpenAPI spec.
Returns:
List[Document]: A list of Document objects.
"""
import yaml
from urllib.parse import urlparse
if uri.startswith("http"):
import requests
response = requests.get(uri)
if response.status_code != 200:
raise ValueError(
"Could not initialize OpenAPIActionToolSpec: "
f"Failed to load OpenAPI spec from {uri}, status code: {response.status_code}"
)
spec = yaml.safe_load(response.text)
elif uri.startswith("file"):
filepath = urlparse(uri).path
with open(filepath, "r") as file:
spec = yaml.safe_load(file)
else:
raise ValueError(
"Could not initialize OpenAPIActionToolSpec: Invalid OpenAPI URI provided. "
"Only HTTP and file path are supported."
)
# Add the servers to the whitelist
try:
servers = [
urlparse(server["url"]).netloc for server in spec.get("servers", [])
]
except KeyError as e:
raise ValueError(
"Could not initialize OpenAPIActionToolSpec: Invalid OpenAPI spec provided. "
"Could not get `servers` from the spec."
) from e
return spec, servers
@@ -1,73 +0,0 @@
"""Open Meteo weather map tool spec."""
import logging
import requests
import pytz
from llama_index.core.tools import FunctionTool
logger = logging.getLogger(__name__)
class OpenMeteoWeather:
geo_api = "https://geocoding-api.open-meteo.com/v1"
weather_api = "https://api.open-meteo.com/v1"
@classmethod
def _get_geo_location(cls, location: str) -> dict:
"""Get geo location from location name."""
params = {"name": location, "count": 10, "language": "en", "format": "json"}
response = requests.get(f"{cls.geo_api}/search", params=params)
if response.status_code != 200:
raise Exception(f"Failed to fetch geo location: {response.status_code}")
else:
data = response.json()
result = data["results"][0]
geo_location = {
"id": result["id"],
"name": result["name"],
"latitude": result["latitude"],
"longitude": result["longitude"],
}
return geo_location
@classmethod
def get_weather_information(cls, location: str) -> dict:
"""Use this function to get the weather of any given location.
Note that the weather code should follow WMO Weather interpretation codes (WW):
0: Clear sky
1, 2, 3: Mainly clear, partly cloudy, and overcast
45, 48: Fog and depositing rime fog
51, 53, 55: Drizzle: Light, moderate, and dense intensity
56, 57: Freezing Drizzle: Light and dense intensity
61, 63, 65: Rain: Slight, moderate and heavy intensity
66, 67: Freezing Rain: Light and heavy intensity
71, 73, 75: Snow fall: Slight, moderate, and heavy intensity
77: Snow grains
80, 81, 82: Rain showers: Slight, moderate, and violent
85, 86: Snow showers slight and heavy
95: Thunderstorm: Slight or moderate
96, 99: Thunderstorm with slight and heavy hail
"""
logger.info(
f"Calling open-meteo api to get weather information of location: {location}"
)
geo_location = cls._get_geo_location(location)
timezone = pytz.timezone("UTC").zone
params = {
"latitude": geo_location["latitude"],
"longitude": geo_location["longitude"],
"current": "temperature_2m,weather_code",
"hourly": "temperature_2m,weather_code",
"daily": "weather_code",
"timezone": timezone,
}
response = requests.get(f"{cls.weather_api}/forecast", params=params)
if response.status_code != 200:
raise Exception(
f"Failed to fetch weather information: {response.status_code}"
)
return response.json()
def get_tools(**kwargs):
return [FunctionTool.from_defaults(OpenMeteoWeather.get_weather_information)]
+5 -6
View File
@@ -1,10 +1,9 @@
import os
import yaml
import json
import importlib
from cachetools import cached, LRUCache
from llama_index.core.tools.tool_spec.base import BaseToolSpec
import os
import yaml
from llama_index.core.tools.function_tool import FunctionTool
from llama_index.core.tools.tool_spec.base import BaseToolSpec
class ToolType:
@@ -46,7 +45,7 @@ class ToolFactory:
def from_env() -> list[FunctionTool]:
tools = []
if os.path.exists("config/tools.yaml"):
with open("config/tools.yaml", "r") as f:
with open("config/tools.yaml", "r", encoding='UTF-8') as f:
tool_configs = yaml.safe_load(f)
if tool_configs != None and len(tool_configs.items()) != 0:
for tool_type, config_entries in tool_configs.items():
+27 -10
View File
@@ -2,15 +2,17 @@ import os
from llama_index.vector_stores.chroma import ChromaVectorStore
from llama_index.vector_stores.qdrant import QdrantVectorStore
from qdrant_client import qdrant_client
from llama_index.graph_stores.neo4j import Neo4jPropertyGraphStore
qclient = None
def get_qdrant_vector_store():
collection_name = os.getenv("VECTOR_STORE_COLLECTION", "default")
def get_qdrant_vector_store(docType:str):
collection_name = docType
llm_query = os.getenv('LLM_QUERY_WAY','rag')
vector_store_path = os.getenv("VECTOR_STORE_PATH")
host=os.getenv("VECTOR_STORE_HOST", "127.0.0.1"),
port=int(os.getenv("VECTOR_STORE_PORT", "6333")),
vector_store_path =os.path.join(vector_store_path,llm_query,docType)
if not vector_store_path or not host:
raise ValueError(
"Please provide either VECTOR_STORE_PATH or VECTOR_STORE_HOST and VECTOR_STORE_PORT"
@@ -32,9 +34,10 @@ def get_qdrant_vector_store():
vector_store = QdrantVectorStore(client=qclient, collection_name=collection_name)
return vector_store
def get_chroma_vector_store():
collection_name = os.getenv("VECTOR_STORE_COLLECTION", "default")
vector_store_path = os.getenv("VECTOR_STORE_PATH")
def get_chroma_vector_store(docType:str):
collection_name = docType
llm_query = os.getenv('LLM_QUERY_WAY','rag')
vector_store_path =os.path.join(os.getenv("VECTOR_STORE_PATH"),llm_query,docType)
# if VECTOR_STORE_PATH is set, use a local ChromaVectorStore from the path
# otherwise, use a remote ChromaVectorStore (ChromaDB Cloud is not supported yet)
if vector_store_path:
@@ -55,17 +58,31 @@ def get_chroma_vector_store():
)
return store
def get_vector_store():
def get_vector_store(docType:str):
store_type=os.getenv("VECTOR_STORE_TYPE")
store = None
match store_type:
case "chroma":
store = get_chroma_vector_store()
store = get_chroma_vector_store(docType)
case "qdrant":
store = get_qdrant_vector_store()
store = get_qdrant_vector_store(docType)
case _:
raise ValueError(f"Invalid vector store type: {store_type}")
return store
def get_Neo4j_Graph_Store(docType:str):
from neo4j import GraphDatabase
driver = GraphDatabase.driver(os.getenv('NEO4J_URL'), auth=(os.getenv('NEO4J_USERNAME'), os.getenv('NEO4J_PASSWORD')))
with driver.session() as session:
session.run("MATCH (n) DETACH DELETE n")
driver.close()
neo4jStore = Neo4jPropertyGraphStore(
username= os.getenv('NEO4J_USERNAME'),
password= os.getenv('NEO4J_PASSWORD'),
url=os.getenv('NEO4J_URL'),
database= docType
)
return neo4jStore
+209 -110
View File
@@ -1,136 +1,169 @@
import os
from typing import Dict
from abc import abstractmethod
from llama_index.core.constants import DEFAULT_TEMPERATURE
from llama_index.core.settings import Settings
from llama_index.llms.xinference import Xinference
from llama_index.embeddings.xinference import XinferenceEmbedding
#from llama_index.llms.xinference import Xinference
from app.engine.model.xinference import XinferenceModel
from app.engine.rerank.xinferenceRerank import CustomXinFerenceRerank
from llama_index.llms.xinference.base import DEFAULT_XINFERENCE_TEMP
from app.xinference.base import XinferenceEmbedding, XinferenceRerank
from app.engine.loaders import getProjectInfos
from app.api.routers.request.base import ProjectInfo
from modelProvide.customDashScope import CustomDashScope
from util.register import *
from llama_index.core.callbacks import CallbackManager
def get_node_postprocessors():
rerank_enabled = os.getenv("RERANK_ENABLED").title()
if rerank_enabled is None or rerank_enabled == 'False':
return []
rerank_model = os.getenv("RERANK_MODEL")
rerank_url = os.getenv("RERANK_BASE_URL")
rerank_top_n = os.getenv("RERANK_TOP_N")
rerank_threshold = os.getenv("RERANK_THRESHOLD")
postprocess = None
if rerank_model is not None:
postprocess = [XinferenceRerank(rerank_model, rerank_url, top_n=rerank_top_n, threshold=rerank_threshold)]
return postprocess
ModelPlateCategory = '模型平台'
def init_settings():
model_provider = os.getenv("MODEL_PROVIDER")
match model_provider:
case "openai":
init_openai()
case "dashscope":
init_dashscope()
case "groq":
init_groq()
case "ollama":
init_ollama()
case "anthropic":
init_anthropic()
case "gemini":
init_gemini()
case "mistral":
init_mistral()
case "azure-openai":
init_azure_openai()
case "t-systems":
from .llmhub import init_llmhub
init_llmhub()
case "xinference":
init_xinference()
case _:
modelPaltCls:ModelPlatform = ClsRegister.get(ModelPlateCategory,model_provider)
if modelPaltCls is not None:
modelPalt:ModelPlatform = modelPaltCls()
Settings.llm = modelPalt.model()
else:
raise ValueError(f"Invalid model provider: {model_provider}")
embedding_provider = os.getenv("EMBEDDING_PROVIDER")
modelPaltCls:ModelPlatform = ClsRegister.get(ModelPlateCategory,embedding_provider)
if modelPalt is not None:
modelPalt:ModelPlatform = modelPaltCls()
Settings.embed_model = modelPalt.embedding()
else:
raise ValueError(f"Invalid embedding provider: {embedding_provider}")
Settings.llm.callback_manager = CallbackManager()
Settings.chunk_size = int(os.getenv("CHUNK_SIZE", "1024"))
Settings.chunk_overlap = int(os.getenv("CHUNK_OVERLAP", "20"))
class ModelPlatform:
@abstractmethod
def model(self):
pass
def init_ollama():
# from llama_index.embeddings.ollama import OllamaEmbedding
# from llama_index.llms.ollama.base import DEFAULT_REQUEST_TIMEOUT, Ollama
#
@abstractmethod
def embedding(self):
pass
@abstractmethod
def rerank(self):
pass
@register(ModelPlateCategory,'ollama')
class OllamaPlatform(ModelPlatform):
def model(self):
from llama_index.llms.ollama.base import DEFAULT_REQUEST_TIMEOUT, Ollama
base_url = os.getenv("OLLAMA_BASE_URL") or "http://127.0.0.1:11434"
request_timeout = float(
os.getenv("OLLAMA_REQUEST_TIMEOUT", DEFAULT_REQUEST_TIMEOUT)
)
Settings.llm = Ollama(
base_url=base_url, model=os.getenv("MODEL"), request_timeout=request_timeout
)
pass
def embedding(self):
#from llama_index.embeddings.ollama import OllamaEmbedding
# base_url = os.getenv("OLLAMA_BASE_URL") or "http://127.0.0.1:11434"
# request_timeout = float(
# os.getenv("OLLAMA_REQUEST_TIMEOUT", DEFAULT_REQUEST_TIMEOUT)
# )
# Settings.embed_model = OllamaEmbedding(
# base_url=base_url,
# model_name=os.getenv("EMBEDDING_MODEL"),
# )
# Settings.llm = Ollama(
# base_url=base_url, model=os.getenv("MODEL"), request_timeout=request_timeout
# )
pass
def init_xinference():
def rerank(self):
from app.engine.rerank.ollamRerank import OllamaRerank
modelpath = os.getcwd() + os.getenv('RERANK_MODEL')
top_n = os.getenv('RERANK_TOP_N',5)
threshold = float(os.getenv('RERANK_THRESHOLD',0.3))
rerank = OllamaRerank(
model=modelpath,
top_n=top_n,
device="cpu",
score_threshold= threshold
)
return [rerank]
@register(ModelPlateCategory,'xinference')
class XinferencePlatform(ModelPlatform):
def model(self):
base_url = os.getenv("BASE_URL")
model = os.getenv("MODEL")
max_tokens = int(os.getenv("LLM_MAX_TOKENS")) if os.getenv("LLM_MAX_TOKENS") is not None else None
temperature = float(os.getenv("LLM_TEMPERATURE", DEFAULT_XINFERENCE_TEMP))
return XinferenceModel(model_uid = model,endpoint = base_url,temperature = temperature,max_tokens = max_tokens)
Settings.llm = Xinference(model, base_url, temperature, max_tokens)
def embedding(self):
base_url = os.getenv("BASE_URL")
embedding_base_url = os.getenv("EMBEDDING_BASE_URL")
embedding_base_url = embedding_base_url if embedding_base_url != None and embedding_base_url != "" else base_url
embed_model_name = os.getenv("EMBEDDING_MODEL")
dimensions = os.getenv("EMBEDDING_DIM")
dimensions = int(dimensions) if dimensions is not None else None
Settings.embed_model = XinferenceEmbedding(embed_model_name, embedding_base_url, dimensions=dimensions)
return XinferenceEmbedding(embed_model_name, embedding_base_url)
def init_openai():
def rerank(self):
rerank_model = os.getenv("RERANK_MODEL")
rerank_url = os.getenv("RERANK_BASE_URL")
rerank_top_n = os.getenv("RERANK_TOP_N")
rerank_threshold = os.getenv("RERANK_THRESHOLD")
postprocess = None
if rerank_model is not None:
postprocess = [CustomXinFerenceRerank(model = rerank_model, base_url = rerank_url, top_n=rerank_top_n,score_threshold=rerank_threshold)]
return postprocess
@register(ModelPlateCategory,'openai')
class OpenAIPlatform(ModelPlatform):
def model(self):
from llama_index.core.constants import DEFAULT_TEMPERATURE
from app.engine.model.siliconCloudOpenAI import SiliconCloudOpenAI
return SiliconCloudOpenAI(api_key= os.getenv('OPENAI_API_KEY'),
api_base= os.getenv('BASE_URL'),
model= os.getenv('MODEL'),
temperature = float(os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)))
def embedding(self):
from llama_index.embeddings.openai import OpenAIEmbedding
from llama_index.llms.openai import OpenAI
return OpenAIEmbedding(api_key=os.getenv('OPENAI_API_KEY'),
api_base= os.getenv('EMBEDDING_BASE_URL'),
model_name = os.getenv('EMBEDDING_MODEL'),
dimensions= int(os.getenv("EMBEDDING_DIM")))
max_tokens = os.getenv("LLM_MAX_TOKENS")
config = {
"model": os.getenv("MODEL"),
"temperature": float(os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)),
"max_tokens": int(max_tokens) if max_tokens is not None else None,
}
Settings.llm = OpenAI(**config)
def rerank(self):
from app.engine.rerank.siliconCloudRerank import SiliconCloudRerank
postprocess = [SiliconCloudRerank(top_n = int(os.getenv('RERANK_TOP_N',5)),
model = os.getenv('RERANK_MODEL'),
base_url = os.getenv('RERANK_BASE_URL'),
api_key = os.getenv('OPENAI_API_KEY')
)]
return postprocess
dimensions = os.getenv("EMBEDDING_DIM")
config = {
"model": os.getenv("EMBEDDING_MODEL"),
"dimensions": int(dimensions) if dimensions is not None else None,
}
Settings.embed_model = OpenAIEmbedding(**config)
@register(ModelPlateCategory,'dashscope')
class DashscopePlatform(ModelPlatform):
def model(self):
apikey = os.getenv('DASHSCOPE_API_KEY')
modelName = os.getenv('MODEL')
return CustomDashScope(model_name=modelName,api_key = apikey)
def init_dashscope():
from llama_index.llms.dashscope import DashScope,DashScopeGenerationModels
from llama_index.embeddings.dashscope import DashScopeEmbedding,DashScopeBatchTextEmbeddingModels,DashScopeTextEmbeddingType,DashScopeTextEmbeddingModels
def embedding(self):
from llama_index.embeddings.dashscope import DashScopeEmbedding,DashScopeTextEmbeddingType,DashScopeTextEmbeddingModels
api_key = os.getenv('DASHSCOPE_API_KEY')
modelName = os.getenv('EMBEDDING_MODEL')
return DashScopeEmbedding(model_name=modelName,
text_type=DashScopeTextEmbeddingType.TEXT_TYPE_QUERY,api_key = api_key)
max_tokens = os.getenv("LLM_MAX_TOKENS")
config = {
"model": os.getenv("MODEL"),
"temperature": float(os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)),
"max_tokens": int(max_tokens) if max_tokens is not None else None,
}
Settings.llm = llm = DashScope(model_name=DashScopeGenerationModels.QWEN_MAX)
def rerank(self):
pass
dimensions = os.getenv("EMBEDDING_DIM")
config = {
"model": os.getenv("EMBEDDING_MODEL"),
"dimensions": int(dimensions) if dimensions is not None else None,
}
Settings.embed_model = DashScopeEmbedding(model_name=DashScopeTextEmbeddingModels.TEXT_EMBEDDING_V2,
text_type=DashScopeTextEmbeddingType.TEXT_TYPE_QUERY)
def init_azure_openai():
@register(ModelPlateCategory,'azure-openai')
class AzureOpenaiPlatform(ModelPlatform):
def model(self):
# from llama_index.core.constants import DEFAULT_TEMPERATURE
# from llama_index.embeddings.azure_openai import AzureOpenAIEmbedding
# from llama_index.llms.azure_openai import AzureOpenAI
#
# llm_deployment = os.environ["AZURE_OPENAI_LLM_DEPLOYMENT"]
@@ -146,15 +179,32 @@ def init_azure_openai():
# or os.getenv("OPENAI_API_VERSION"),
# }
#
# Settings.llm = AzureOpenAI(
# return AzureOpenAI(
# model=os.getenv("MODEL"),
# max_tokens=int(max_tokens) if max_tokens is not None else None,
# temperature=float(temperature),
# deployment_name=llm_deployment,
# **azure_config,
# )
pass
def embedding(self):
# from llama_index.core.constants import DEFAULT_TEMPERATURE
# from llama_index.embeddings.azure_openai import AzureOpenAIEmbedding
#
# Settings.embed_model = AzureOpenAIEmbedding(
# llm_deployment = os.environ["AZURE_OPENAI_LLM_DEPLOYMENT"]
# embedding_deployment = os.environ["AZURE_OPENAI_EMBEDDING_DEPLOYMENT"]
# max_tokens = os.getenv("LLM_MAX_TOKENS")
# temperature = os.getenv("LLM_TEMPERATURE", DEFAULT_TEMPERATURE)
# dimensions = os.getenv("EMBEDDING_DIM")
#
# azure_config = {
# "api_key": os.environ["AZURE_OPENAI_KEY"],
# "azure_endpoint": os.environ["AZURE_OPENAI_ENDPOINT"],
# "api_version": os.getenv("AZURE_OPENAI_API_VERSION")
# or os.getenv("OPENAI_API_VERSION"),
# }
# return AzureOpenAIEmbedding(
# model=os.getenv("EMBEDDING_MODEL"),
# dimensions=int(dimensions) if dimensions is not None else None,
# deployment_name=embedding_deployment,
@@ -162,11 +212,17 @@ def init_azure_openai():
# )
pass
def rerank(self):
pass
def init_fastembed():
"""
Use Qdrant Fastembed as the local embedding provider.
"""
@register(ModelPlateCategory,'fastembed')
class FastembedPlatform(ModelPlatform):
@abstractmethod
def model(self):
pass
@abstractmethod
def embedding(self):
# from llama_index.embeddings.fastembed import FastEmbedEmbedding
#
# embed_model_map: Dict[str, str] = {
@@ -182,8 +238,14 @@ def init_fastembed():
# )
pass
@abstractmethod
def rerank(self):
pass
def init_groq():
@register(ModelPlateCategory,'groq')
class GroqPlatform(ModelPlatform):
@abstractmethod
def model(self):
# from llama_index.llms.groq import Groq
#
# model_map: Dict[str, str] = {
@@ -197,8 +259,17 @@ def init_groq():
# init_fastembed()
pass
@abstractmethod
def embedding(self):
pass
def init_anthropic():
@abstractmethod
def rerank(self):
pass
@register(ModelPlateCategory,'anthropic')
class AnthropicPlatform(ModelPlatform):
def model(self):
# from llama_index.llms.anthropic import Anthropic
#
# model_map: Dict[str, str] = {
@@ -214,22 +285,50 @@ def init_anthropic():
# init_fastembed()
pass
def embedding(self):
pass
def init_gemini():
# from llama_index.embeddings.gemini import GeminiEmbedding
def rerank(self):
pass
@register(ModelPlateCategory,'gemini')
class GeminiPlatform(ModelPlatform):
def model(self):
# from llama_index.llms.gemini import Gemini
#
# model_name = f"models/{os.getenv('MODEL')}"
# embed_model_name = f"models/{os.getenv('EMBEDDING_MODEL')}"
#
# Settings.llm = Gemini(model=model_name)
# Settings.embed_model = GeminiEmbedding(model_name=embed_model_name)
# return Gemini(model=model_name)
pass
def init_mistral():
# from llama_index.embeddings.mistralai import MistralAIEmbedding
# from llama_index.llms.mistralai import MistralAI
#
# Settings.llm = MistralAI(model=os.getenv("MODEL"))
# Settings.embed_model = MistralAIEmbedding(model_name=os.getenv("EMBEDDING_MODEL"))
def embedding(self):
# from llama_index.embeddings.gemini import GeminiEmbedding
# embed_model_name = f"models/{os.getenv('EMBEDDING_MODEL')}"
# return GeminiEmbedding(model_name=embed_model_name)
pass
def rerank(self):
pass
@register(ModelPlateCategory,'mistral')
class MistralPlatform(ModelPlatform):
def model(self):
# from llama_index.llms.mistralai import MistralAI
# return MistralAI(model=os.getenv("MODEL"))
pass
def embedding(self):
# from llama_index.embeddings.mistralai import MistralAIEmbedding
# return MistralAIEmbedding(model_name=os.getenv("EMBEDDING_MODEL"))
pass
def rerank(self):
pass
def init_ProjectInfo():
prjObj = ProjectInfo()
prjInfos:list[tuple] = getProjectInfos()
for prjInfo in prjInfos:
prjObj.add(prjInfo['name'],prjInfo['flag'])
@@ -1,272 +0,0 @@
"""Xinference embeddings file."""
import logging
from enum import Enum
from http import HTTPStatus
from typing import Any, Dict, List, Optional, Union, Tuple
from llama_index.core.base.embeddings.base import BaseEmbedding, Embedding, dispatcher
from llama_index.core.bridge.pydantic import PrivateAttr
from llama_index.core.callbacks import CBEventType, EventPayload
from llama_index.core.embeddings.multi_modal_base import MultiModalEmbedding
from llama_index.core.instrumentation.events.rerank import ReRankStartEvent, ReRankEndEvent
from llama_index.core.postprocessor.types import BaseNodePostprocessor
from llama_index.core.schema import ImageType, NodeWithScore, QueryBundle
from pydantic import Field
logger = logging.getLogger(__name__)
EMBED_MAX_INPUT_LENGTH = 2048
EMBED_MAX_BATCH_SIZE = 1
class XinferenceEmbedding(BaseEmbedding):
"""Xinference class for text embedding.
"""
model_description: Dict[str, Any] = Field(
description="The model description from Xinference."
)
_generator: Any = PrivateAttr()
_model_uid: str = Field(description="The Xinference model to use.")
_endpoint: str = Field(description="The Xinference endpoint URL to use.")
def __init__(
self,
model_uid: str,
endpoint: str,
embed_batch_size: int = EMBED_MAX_BATCH_SIZE,
dimensions: Optional[int] = None,
additional_kwargs: Optional[Dict[str, Any]] = None,
api_key: Optional[str] = None,
api_base: Optional[str] = None,
api_version: Optional[str] = None,
max_retries: int = 10,
# timeout: float = 60.0,
# reuse_client: bool = True,
# callback_manager: Optional[CallbackManager] = None,
# default_headers: Optional[Dict[str, str]] = None,
# http_client: Optional[httpx.Client] = None,
# async_http_client: Optional[httpx.AsyncClient] = None,
# num_workers: Optional[int] = None,
**kwargs: Any,
) -> None:
generator, model_description, embed_batch_size, dimensions = self.load_model(
model_uid, endpoint
)
self._generator = generator
#self._model_uid = model_uid
#self._endpoint = endpoint
super().__init__(
embed_batch_size=embed_batch_size,
dimensions=dimensions,
#callback_manager=callback_manager,
model_name=model_uid,
additional_kwargs=additional_kwargs,
api_key=api_key,
api_base=api_base,
api_version=api_version,
max_retries=max_retries,
# reuse_client=reuse_client,
# timeout=timeout,
# default_headers=default_headers,
# num_workers=num_workers,
**kwargs,
)
def load_model(self, model_uid: str, endpoint: str) -> Tuple[Any, int, dict]:
try:
from xinference.client import RESTfulClient
except ImportError:
raise ImportError(
"Could not import Xinference library."
'Please install Xinference with `pip install "xinference[all]"`'
)
client = RESTfulClient(endpoint)
try:
assert isinstance(client, RESTfulClient)
except AssertionError:
raise RuntimeError(
"Could not create RESTfulClient instance."
"Please make sure Xinference endpoint is running at the correct port."
)
generator = client.get_model(model_uid)
model_description = client.list_models()[model_uid]
try:
assert generator is not None
assert model_description is not None
except AssertionError:
raise RuntimeError(
"Could not get model from endpoint."
"Please make sure Xinference endpoint is running at the correct port."
)
model = model_description["model_name"]
replica = model_description['replica']
dimensions = model_description['dimensions']
max_tokens = model_description['max_tokens']
return generator, model_description, replica, dimensions
@classmethod
def class_name(cls) -> str:
return "XinferenceEmbedding"
def _get_text_embedding(self, text: str) -> Embedding:
"""
Embed the input text synchronously.
Subclasses should implement this method. Reference get_text_embedding's
docstring for more information.
"""
assert self._generator is not None
response = self._generator.create_embedding(input=text)
return response['data'][0]['embedding']
def _get_query_embedding(self, query: str) -> Embedding:
"""
Embed the input query synchronously.
Subclasses should implement this method. Reference get_query_embedding's
docstring for more information.
"""
return self._get_text_embedding(query)
async def _aget_query_embedding(self, query: str) -> Embedding:
"""
Embed the input query asynchronously.
Subclasses should implement this method. Reference get_query_embedding's
docstring for more information.
"""
return self._get_query_embedding(query)
class XinferenceRerank(BaseNodePostprocessor):
"""Xinference class for rerank.
"""
model_description: Dict[str, Any] = Field(
description="The model description from Xinference."
)
_generator: Any = PrivateAttr()
_model_uid: str = Field(description="The Xinference model to use.")
_endpoint: str = Field(description="The Xinference endpoint URL to use.")
model: str = Field(description="Dashscope rerank model name.")
top_n: int = Field(description="Top N nodes to return.")
threshold: float = Field(description="threshold nodes to return.")
def __init__(
self,
model_uid: str,
endpoint: str,
top_n: int = None,
threshold: float = None,
return_documents: bool = False
):
_model_uid = model_uid
_endpoint = endpoint
_op_n = top_n
threshold = threshold
generator, model_description = self.load_model(
model_uid, endpoint
)
self._generator = generator
super().__init__(top_n=top_n, model=model_uid, model_uid=model_uid, threshold = threshold, return_documents=return_documents)
@classmethod
def class_name(cls) -> str:
return "XinferenceRerank"
def _postprocess_nodes(
self,
nodes: List[NodeWithScore],
query_bundle: Optional[QueryBundle] = None,
) -> List[NodeWithScore]:
if query_bundle is None:
raise ValueError("Missing query bundle in extra info.")
if len(nodes) == 0:
return []
dispatcher.event(
ReRankStartEvent(
nodes = nodes,
top_n = self.top_n,
query = query_bundle,
model_name = self.model
)
)
with self.callback_manager.event(
CBEventType.RERANKING,
payload={
EventPayload.NODES: nodes,
EventPayload.MODEL_NAME: self._model_uid,
EventPayload.QUERY_STR: query_bundle.query_str,
EventPayload.TOP_K: self.top_n,
},
) as event:
texts = [node.node.get_content() for node in nodes]
response = self._generator.rerank(texts,query_bundle.query_str)
new_nodes = []
for result in response['results']:
new_node_with_score = NodeWithScore(
node=nodes[result['index']].node, score=result['relevance_score']
)
if self.threshold is not None:
if new_node_with_score.score >=self.threshold:
new_nodes.append(new_node_with_score)
if self.top_n is not None:
if len(new_nodes) > self.top_n:
for index in new_nodes[self.top_n:-1]:
new_nodes.remove(index)
event.on_end(payload={EventPayload.NODES: new_nodes})
dispatcher.event(
ReRankEndEvent(
nodes= new_nodes
)
)
return new_nodes
def load_model(self, model_uid: str, endpoint: str) -> Tuple[Any, int, dict]:
try:
from xinference.client import RESTfulClient
except ImportError:
raise ImportError(
"Could not import Xinference library."
'Please install Xinference with `pip install "xinference[all]"`'
)
client = RESTfulClient(endpoint)
try:
assert isinstance(client, RESTfulClient)
except AssertionError:
raise RuntimeError(
"Could not create RESTfulClient instance."
"Please make sure Xinference endpoint is running at the correct port."
)
generator = client.get_model(model_uid)
model_description = client.list_models()[model_uid]
try:
assert generator is not None
assert model_description is not None
except AssertionError:
raise RuntimeError(
"Could not get model from endpoint."
"Please make sure Xinference endpoint is running at the correct port."
)
model = model_description["model_name"]
return generator, model_description
View File
-272
View File
@@ -1,272 +0,0 @@
"""Xinference embeddings file."""
import logging
from enum import Enum
from http import HTTPStatus
from typing import Any, Dict, List, Optional, Union, Tuple
from llama_index.core.base.embeddings.base import BaseEmbedding, Embedding, dispatcher
from llama_index.core.bridge.pydantic import PrivateAttr
from llama_index.core.callbacks import CBEventType, EventPayload
from llama_index.core.embeddings.multi_modal_base import MultiModalEmbedding
from llama_index.core.instrumentation.events.rerank import ReRankStartEvent, ReRankEndEvent
from llama_index.core.postprocessor.types import BaseNodePostprocessor
from llama_index.core.schema import ImageType, NodeWithScore, QueryBundle
from pydantic import Field
logger = logging.getLogger(__name__)
EMBED_MAX_INPUT_LENGTH = 2048
EMBED_MAX_BATCH_SIZE = 1
class XinferenceEmbedding(BaseEmbedding):
"""Xinference class for text embedding.
"""
model_description: Dict[str, Any] = Field(
description="The model description from Xinference."
)
_generator: Any = PrivateAttr()
_model_uid: str = Field(description="The Xinference model to use.")
_endpoint: str = Field(description="The Xinference endpoint URL to use.")
def __init__(
self,
model_uid: str,
endpoint: str,
embed_batch_size: int = EMBED_MAX_BATCH_SIZE,
dimensions: Optional[int] = None,
additional_kwargs: Optional[Dict[str, Any]] = None,
api_key: Optional[str] = None,
api_base: Optional[str] = None,
api_version: Optional[str] = None,
max_retries: int = 10,
# timeout: float = 60.0,
# reuse_client: bool = True,
# callback_manager: Optional[CallbackManager] = None,
# default_headers: Optional[Dict[str, str]] = None,
# http_client: Optional[httpx.Client] = None,
# async_http_client: Optional[httpx.AsyncClient] = None,
# num_workers: Optional[int] = None,
**kwargs: Any,
) -> None:
generator, model_description, embed_batch_size, dimensions = self.load_model(
model_uid, endpoint
)
self._generator = generator
#self._model_uid = model_uid
#self._endpoint = endpoint
super().__init__(
embed_batch_size=embed_batch_size,
dimensions=dimensions,
#callback_manager=callback_manager,
model_name=model_uid,
additional_kwargs=additional_kwargs,
api_key=api_key,
api_base=api_base,
api_version=api_version,
max_retries=max_retries,
# reuse_client=reuse_client,
# timeout=timeout,
# default_headers=default_headers,
# num_workers=num_workers,
**kwargs,
)
def load_model(self, model_uid: str, endpoint: str) -> Tuple[Any, int, dict]:
try:
from xinference.client import RESTfulClient
except ImportError:
raise ImportError(
"Could not import Xinference library."
'Please install Xinference with `pip install "xinference[all]"`'
)
client = RESTfulClient(endpoint)
try:
assert isinstance(client, RESTfulClient)
except AssertionError:
raise RuntimeError(
"Could not create RESTfulClient instance."
"Please make sure Xinference endpoint is running at the correct port."
)
generator = client.get_model(model_uid)
model_description = client.list_models()[model_uid]
try:
assert generator is not None
assert model_description is not None
except AssertionError:
raise RuntimeError(
"Could not get model from endpoint."
"Please make sure Xinference endpoint is running at the correct port."
)
model = model_description["model_name"]
replica = model_description['replica']
dimensions = model_description['dimensions']
max_tokens = model_description['max_tokens']
return generator, model_description, replica, dimensions
@classmethod
def class_name(cls) -> str:
return "XinferenceEmbedding"
def _get_text_embedding(self, text: str) -> Embedding:
"""
Embed the input text synchronously.
Subclasses should implement this method. Reference get_text_embedding's
docstring for more information.
"""
assert self._generator is not None
response = self._generator.create_embedding(input=text)
return response['data'][0]['embedding']
def _get_query_embedding(self, query: str) -> Embedding:
"""
Embed the input query synchronously.
Subclasses should implement this method. Reference get_query_embedding's
docstring for more information.
"""
return self._get_text_embedding(query)
async def _aget_query_embedding(self, query: str) -> Embedding:
"""
Embed the input query asynchronously.
Subclasses should implement this method. Reference get_query_embedding's
docstring for more information.
"""
return self._get_query_embedding(query)
class XinferenceRerank(BaseNodePostprocessor):
"""Xinference class for rerank.
"""
model_description: Dict[str, Any] = Field(
description="The model description from Xinference."
)
_generator: Any = PrivateAttr()
_model_uid: str = Field(description="The Xinference model to use.")
_endpoint: str = Field(description="The Xinference endpoint URL to use.")
model: str = Field(description="Dashscope rerank model name.")
top_n: int = Field(description="Top N nodes to return.")
threshold: float = Field(description="threshold nodes to return.")
def __init__(
self,
model_uid: str,
endpoint: str,
top_n: int = None,
threshold: float = None,
return_documents: bool = False
):
_model_uid = model_uid
_endpoint = endpoint
_op_n = top_n
threshold = threshold
generator, model_description = self.load_model(
model_uid, endpoint
)
self._generator = generator
super().__init__(top_n=top_n, model=model_uid, model_uid=model_uid, threshold = threshold, return_documents=return_documents)
@classmethod
def class_name(cls) -> str:
return "XinferenceRerank"
def _postprocess_nodes(
self,
nodes: List[NodeWithScore],
query_bundle: Optional[QueryBundle] = None,
) -> List[NodeWithScore]:
if query_bundle is None:
raise ValueError("Missing query bundle in extra info.")
if len(nodes) == 0:
return []
dispatcher.event(
ReRankStartEvent(
nodes = nodes,
top_n = self.top_n,
query = query_bundle,
model_name = self.model
)
)
with self.callback_manager.event(
CBEventType.RERANKING,
payload={
EventPayload.NODES: nodes,
EventPayload.MODEL_NAME: self._model_uid,
EventPayload.QUERY_STR: query_bundle.query_str,
EventPayload.TOP_K: self.top_n,
},
) as event:
texts = [node.node.get_content() for node in nodes]
response = self._generator.rerank(texts,query_bundle.query_str)
new_nodes = []
for result in response['results']:
new_node_with_score = NodeWithScore(
node=nodes[result['index']].node, score=result['relevance_score']
)
if self.threshold is not None:
if new_node_with_score.score >=self.threshold:
new_nodes.append(new_node_with_score)
if self.top_n is not None:
if len(new_nodes) > self.top_n:
for index in new_nodes[self.top_n:-1]:
new_nodes.remove(index)
event.on_end(payload={EventPayload.NODES: new_nodes})
dispatcher.event(
ReRankEndEvent(
nodes= new_nodes
)
)
return new_nodes
def load_model(self, model_uid: str, endpoint: str) -> Tuple[Any, int, dict]:
try:
from xinference.client import RESTfulClient
except ImportError:
raise ImportError(
"Could not import Xinference library."
'Please install Xinference with `pip install "xinference[all]"`'
)
client = RESTfulClient(endpoint)
try:
assert isinstance(client, RESTfulClient)
except AssertionError:
raise RuntimeError(
"Could not create RESTfulClient instance."
"Please make sure Xinference endpoint is running at the correct port."
)
generator = client.get_model(model_uid)
model_description = client.list_models()[model_uid]
try:
assert generator is not None
assert model_description is not None
except AssertionError:
raise RuntimeError(
"Could not get model from endpoint."
"Please make sure Xinference endpoint is running at the correct port."
)
model = model_description["model_name"]
return generator, model_description
+33 -18
View File
@@ -1,33 +1,48 @@
file:
enable: true # 添加 enable 字段
# use_llama_parse: Use LlamaParse if `true`. Needs a `LLAMA_CLOUD_API_KEY` from https://cloud.llamaindex.ai set as environment variable
use_llama_parse: false
db:
#db:
# The configuration for the database loader, only supports MySQL and PostgreSQL databases for now.
# uri: The URI for the database. E.g.: mysql+pymysql://user:password@localhost:3306/db or postgresql+psycopg2://user:password@localhost:5432/db
# query: The query to fetch data from the database. E.g.: SELECT * FROM table
- uri: mysql+pymysql://zjinfo1:Dy2Bcr53Hm5xRkba@110.42.234.166:3306/zjinfo1
#- uri: mysql+pymysql://zjinfo:Y6EAjEEdSYmskA8B@110.42.234.166:3306/zjinfo
# - uri: mysql+pymysql://zjinfo2:GSKcziSdBixDXwcd@110.42.234.166:3306/zjinfo2
queries:
- sql: select * from ProjectProperties limit 30;
explanation: "工程属性表数据,层级关系包含在博微电力造价工程文件格式_ProjectProperties.json文件中。"
#- uri: mysql+pymysql://zjinfo1:Dy2Bcr53Hm5xRkba@110.42.234.166:3306/zjinfo1
#enable: false # 添加 enable 字段
#queries:
#- sql: select * from ProjectProperties;
#explanation: "工程属性表数据,层级关系包含在博微电力造价工程文件格式_ProjectProperties.json文件中。"
- sql: select Id, ParentId, Level, Name, Code, Amount, Amount_Total from TotalCalculateTable;
explanation: "总算表数据,层级关系包含在博微电力造价工程文件格式_TotalCalculateTable.json文件中。"
#- sql: select Id, ParentId, Level, Name, Code, Amount, Amount_Total from TotalCalculateTable;
#explanation: "总算表数据,层级关系包含在博微电力造价工程文件格式_TotalCalculateTable.json文件中。"
- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where Level = 3 and ProfessionalType = '线路' limit 50;
explanation: "专业类型为线路的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
#- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where ProfessionalType = '线路';
#explanation: "专业类型为线路的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
#- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where ProfessionalType = '余物清理';
#explanation: "专业类型为余物清理的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
#- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where ProfessionalType = '拆除线路';
#explanation: "专业类型为拆除线路的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where Level = 3 and ProfessionalType = '余物清理' limit 50;
explanation: "专业类型为余物清理的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
#- sql: select Id, ParentId, Level, Name, Code, Rate, Amount from OtherFee;
#explanation: "其他费用表数据,层级关系包含在博微电力造价工程文件格式_OtherFee.json文件中"
- sql: select Id, ParentId, Level, SerialNumber, Name, Quantity, Rate, Sum_Price from ProjectDivision where Level = 3 and ProfessionalType = '拆除线路' limit 50;
explanation: "专业类型为拆除线路的项目划分表数据,层级关系包含在博微电力造价工程文件格式_ProjectDivision.json文件中。"
- sql: select Id, ParentId, Level, Name, Code, Rate, Amount from OtherFee;
explanation: "其他费用表数据,层级关系包含在博微电力造价工程文件格式_OtherFee.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '线路取费表'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '线路取费表(调试工程)aa'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '大型土石方取费表'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '线路取费表(余物清理)'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '线路取费表(余物清理)(1)'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from FeeCollectionTable where FeeCollection_Table_Name = '线路取费表(拆除)'
#explanation: "取费表名称为线路取费表的取费表数据,层级关系包含在博微电力造价工程文件格式_FeeCollectionTable.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from ProjectQuantities where Professional_Type = '线路'
#explanation: "专业类型为线路的工程量表数据,层级关系包含在博微电力造价工程文件格式_ProjectQuantities.json文件中"
#- sql: select Name, Code, Calculation_Formula, Rate, from ProjectQuantities where Professional_Type = '余物清理'
#explanation: "专业类型为余物清理的工程量表数据,层级关系包含在博微电力造价工程文件格式_ProjectQuantities.json文件中"
#web:
# driver_arguments:
# # The arguments to pass to the webdriver. E.g.: add --headless to run in headless mode
@@ -0,0 +1,96 @@
# 其他费用
备注:其他费用表被称为“工程费用中其他费用明细”。其他费用是指为完成工程项目建设所必需的,但不属于建筑工程费、安装工程费、设备购置费、基本预备费的其他相关费用。包括建设场地征用及清理费、项目建设管理费、项目建设技术服务费、生产准备费、大件运输措施费、专业爆破服务费等。查询示例: SELECT Rate FROM OtherFee WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:nodeType
- 字段名称:relTbId
- 字段名称:parentId
- 字段名称:序号
- 备注:序号,序列号
- 字段名称:名称
- 备注:项目名,费用名,名称
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:金额,价格
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:金额
- 备注:金额,价格
- 字段名称:编码
- 备注:WBS编号,WBS编码
- 字段名称:服务内容
- 字段名称:费用归属
- 字段名称:输出
- 字段名称:不可竞争费用
- 字段名称:编制依据
- 备注:编制依据,编制来源
- 字段名称:备注
- 备注:备注,说明
- 字段名称:表一显示
- 字段名称:税率
|_id|nodeType|relTbId|parentId|序号|名称|代码|单位|取费基数|费率|金额|编码|服务内容|费用归属|输出|不可竞争费用|编制依据|备注|表一显示|税率|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|31ywrqmravb4|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||1|建设场地征用及清理费|A||建设场地征用及清理费|100|16831284.228711|31831000000|||否|否|23eds股份认同||是|0|
|31ywrqmravb5|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||2|项目建设管理费|B|||100|1619697876.652205|31832000000|||否|否|||否|0|
|31ywrqmtsrnk|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.1|项目法人管理费|B1||本体工程费+编制基准期价差|1.17|986923559.414937|31832100000|||否|否|||否|0|
|31ywrqmtsrnl|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.2|招标费|B2||本体工程费+编制基准期价差|0.28|236186834.73178|31832200000|||否|否||线路长度超过500km时,超过部分每增加100km,费率乘以0.92系数 |否|6|
|31ywrqmtsrnm|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.3|工程监理费|B3||工程监理费|100|131009.92|31832300000|||否|否|23eds股份认同|说明:162号文指导费率区间:单回路0.64-0.65(万元/km);同杆(塔)双回0.77-0.78(万元/km)。|否|6|
|31ywrqmtsrnn|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.4|设备材料监造费|B4||监造材料费|0|0|31832400000|||否|否|||否|6|
|31ywrqmwao00|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.5|施工过程造价咨询及竣工结算审核费|B5||本体工程费+编制基准期价差|0.47|396456472.585488|31832500000|||否|否|12|费用计算低于3000元时,按3000元计列。|否|6|
|31ywrqmwao01|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmravb5|2.6|工程保险费|B6|||100|0|31832600000|||否|否|||否|6|
|31ywrqmwao02|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||3|项目建设技术服务费|C|||100|16855957065.430212|31833000000|||否|否|沃尔沃12||否|6|
|31ywrqmwao03|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.1|项目前期工作费|C1|||100|0|31833100000|||否|否|地方||否|6|
|31ywrqmyskcg|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.1|可行性研究费用|C11|||100|0|31833110000|||否|否||说明:162号文指导费用区间:5万元-10万元;10km以上,增加0.2万元/km;多回路、高海拔等可调整。|否|6|
|31ywrqmyskch|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.2|环境影响评价费用|C12|||100|0|31833120000|||否|否||说明:162号文指导费用区间:5万元-8万元;20km以上,增加0.25万元/km;穿越环境敏感区、平行走廊等可调整。|否|6|
|31ywrqmyskci|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.3|建设项目规划选址费|C13|||100|0|31833130000|||否|否||说明:162号文指导费用区间:3万元-10万元;10km以上,增加0.05万元/km;平行走廊等可调整。|否|6|
|31ywrqn1agow|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.4|水土保持方案编审费用|C14|||100|0|31833140000|||否|否|二|说明:162号文指导费用区间:2万元-3万元;10km以上,增加0.1万元/km;平行走廊等可调整。|否|6|
|31ywrqn1agox|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.5|地质灾害危险性评估费用|C15|||100|0|31833150000|||否|否||说明:162号文指导费用区间:1万元-2万元;10km以上,增加0.15万元/km;平行走廊等可调整。|否|6|
|31ywrqn1agoy|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.6|地震安全性评价费用|C16|||100|0|31833160000|||否|否||说明:线路工程原则上不计此费用|否|6|
|31ywrqn3sd1c|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.7|文物调查费用|C17|||100|0|31833170000|||否|否||说明:162号文指导费用区间:2万元-3万元;10km以上,增加0.05-0.15万元/km;平行走廊等可调整。|否|6|
|31ywrqn3sd1d|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.8|矿产压覆评估费用|C18|||100|0|31833180000|||否|否||说明:162号文指导费用区间:3万元-8万元;10km以上,增加0.1-0.3万元/km;平行走廊等可调整。|否|6|
|31ywrqn3sd1e|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.9|用地预审费用|C19|||100|0|31833190000|||否|否||说明:162号文指导费用区间:3万元-5万元;10km以上,增加0.1-0.3万元/km;平行走廊等可调整。|否|6|
|31ywrqn3sd1f|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.10|节能评估费用|C1A|||100|0|318331A0000|||否|否||说明:162号文指导费用区间:2万元-5万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31ywrqn6a9ds|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.11|社会稳定风险评估费用|C1B|||100|0|318331B0000|||否|否||说明:162号文指导费用区间:5万元-10万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31ywrqn6a9dt|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.12|使用林地可行性研究费用|C1C|||100|0|318331C0000|||否|否||说明:162号文指导费用区间:2万元-3万元;10km以上,增加0.05万元/km。|否|6|
|31ywrqn8s5q8|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao03|3.1.13|前期工作管理费用|C1D|||100|0|318331D0000|||否|否||说明:162号文指导费用:5万元;单独的变电站、换流站、输电线路工程按40%-60%调整|否|6|
|31ywrqn8s5q9|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.2|知识产权转让与研究试验费|C2|||100|0|31833200000|||否|否||根据建设项目法人提出的项目和费用计列。|否|6|
|31ywrqn8s5qa|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.3|勘察设计费|C3|||100|16164210209.43|31833300000|||否|否|qwe||否|6|
|31ywrqn8s5qb|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqn8s5qa|3.3.1|勘察费|C31||勘察费|100|12122154260|31833310000|||否|否|zx||否|6|
|31ywrqn8s5qc|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqn8s5qa|3.3.2|设计费|C32||设计费|100|4042055949.43|31833320000|||否|否|asd||否|6|
|31ywrqnba22o|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.4|设计文件评审费|C4|||100|56840|31833400000|||否|否|drf||否|6|
|31ywrqnba22p|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnba22o|3.4.1|可行性研究文件评审费|C41||可行性研究评审费|100|13340|31833410000|||否|否|hf||否|6|
|31ywrqndryf4|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnba22o|3.4.2|初步设计文件评审费|C42||初步设计评审费|100|18560|31833420000|||否|否|vb||否|6|
|31ywrqndryf5|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnba22o|3.4.3|施工图文件评审费|C43||施工图评审费|100|24940|31833430000|||否|否|asdf||否|6|
|31ywrqndryf6|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.5|项目后评价费|C5||本体工程费+编制基准期价差|0.5|421762204.878178|31833500000|||否|否|asd|1.架空交流输电线路长度超过300km时,超过部分乘以0.8系数;架空直流输电线路长度超过1500km时,超过部分乘以0.8系数。 2.单项输变电工程,建筑工程费+安装工程费低于2000万元,取费基数取2000万元。|否|6|
|31ywrqng9urk|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.6|工程建设检测费|C6|||100|185575370.146398|31833600000|||否|否|sd||是|6|
|31ywrqng9url|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqng9urk|3.6.1|电力工程质量检测费|C61||本体工程费+编制基准期价差|0.22|185575370.146398|31833610000|||是|否|e||否|6|
|31ywrqng9urm|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqng9urk|3.6.2|特种设备安全监测费|C62|||100|0|31833620000|||否|否|||是|6|
|31ywrqng9urn|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqng9urk|3.6.3|环境监测及环境保护验收费|C63|||100|0|31833630000|||否|否|||否|6|
|31ywrqng9uro|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqng9urk|3.6.4|水土保持监测及验收费|C64|||100|0|31833640000|||是|否|||是|6|
|31ywrqnirr40|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqng9urk|3.6.5|桩基检测费|C65|||100|0|31833650000|||否|否|||否|6|
|31ywrqnirr41|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqmwao02|3.7|电力工程技术经济标准编制费|C7||本体工程费+编制基准期价差|0.1|84352440.975636|31833700000|||否|否|||否|6|
|31ywrqnirr42|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||4|生产准备费|D|||100|472373669.46356|31834000000|||是|否|||否|0|
|31ywrqnirr43|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnirr42|4.1|管理车辆购置费|D1||本体工程费+编制基准期价差|0.25|210881102.439089|31834100000|||否|否||注:如果管理车辆由项目法人单位统一配置,并且不在工程项目中分摊相关费用时,本项费用不计。|否|13|
|31ywrqnl9ngg|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnirr42|4.2|工器具及办公家具购置费|D2||本体工程费+编制基准期价差|0.21|177140126.048835|31834200000|||否|否|||否|13|
|31ywrqnl9ngh|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnirr42|4.3|生产职工培训及提前进场费|D3||本体工程费+编制基准期价差|0.1|84352440.975636|31834300000|||否|否|||否|0|
|31ywrqnnrjsw|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||5|专业爆破服务费|E|||100|0|31835000000|||否|否|||否|0|
|31ywrqnnrjsx|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||6|其他|F|||100|0|31836000000|||否|否|||否|0|
|31ywrqnnrjsy|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||7|新费用|SD3||本体工程费+编制基准期价差|100|84352440975.635651||||否|否|||否|0|
|31ywrqnq9g5c|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}||8|新费用1||||100|107625611701.459076||||否|否|||否|0|
|31ywrqnq9g5d|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.1|新费用15|||本体工程费|100|55105688268.517624||||否|否|||否|0|
|31ywrqnq9g5e|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.2|新费用2|||设备购置费|100|2567934636.357451||||否|否|||否|0|
|31ywrqnq9g5f|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.3|新费用3|||监造材料费|100|24036.0696||||否|否|||否|0|
|31ywrqnsrchs|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.4|新费用4|||监造设备费|100|15924502.368||||否|否|||否|0|
|31ywrqnsrcht|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.5|新费用5|||甲供主材费含税|100|2220128892.505839||||否|否|||否|0|
|31ywrqnsrchu|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.6|新费用6|||乙供主材费不含税|100|2802065.505122||||否|否|||否|0|
|31ywrqnsrchv|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.7|新费用7|||勘察费|100|12122154260||||否|否|||否|0|
|31ywrqnsrchw|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.8|新费用8|||设计费|100|4042055949.43||||否|否|||否|0|
|31ywrqnv98u8|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.9|新费用9|||基本设计费|100|2285224349.13||||否|否|||否|0|
|31ywrqnv98u9|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.10|新费用10|||建设场地征用及清理费|100|16831284.228711||||否|否|||否|0|
|31ywrqnv98ua|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.11|新费用11|||编制基准期价差|100|29246752707.118019||||否|否|||否|0|
|31ywrqnv98ub|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.12|新费用12|||余物清理费|100|90736.228711||||否|否|||否|0|
|31ywrqnxr56o|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.13|新费用13|||工程税率|100|9||||否|否|||否|0|
|31ywrqnxr56p|其他费用|{0086C94C-6041-44CB-B021-E696A825DF9A}|31ywrqnq9g5c|8.14|新费用14|||线路亘长|100|5||||否|否|||否|0|
@@ -0,0 +1,29 @@
# 大型土石方取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{EA4C703B-0027-4884-9820-9BD4EE91A66B}|FFZ1|||一|否|100|直接工程费|取费表||{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{6DA65B76-41D3-40C8-A9D7-867D0997FFC7}|RGF|取费定额人工费||1|否|100|人工费|取费表|{EA4C703B-0027-4884-9820-9BD4EE91A66B}|{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{AC5B806B-A8C9-46C1-B30B-3A6048389B98}|CLF|取费定额乙供材料费不含税+乙供取费主材费不含税+甲供取费主材费含税||2|否|100|材料费|取费表|{EA4C703B-0027-4884-9820-9BD4EE91A66B}|{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{FE6C418F-D50F-43F0-939E-6E786619FEF0}|JXF|取费定额机械费||3|否|100|施工机械使用费|取费表|{EA4C703B-0027-4884-9820-9BD4EE91A66B}|{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{CC66691E-2C2B-4D5A-8592-F32DF6AF0C32}|TZHQF|FFZ1-甲供主材进项税额|综合取费费用额(包含措施费、间接费、利润)|二|否|17.79|综合取费费用额|取费表||{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{5FA19404-F27F-42C7-AA88-657810C04FBD}|TFFS|FFZ1+TZHQF-甲供取费主材费含税+不取费定额费不含税+不取费乙供主材费不含税||三|否|9|税金|取费表||{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
|{19644FFF-4F8E-4905-9680-FC634E1976FD}|THJ|FFZ1+TZHQF+TFFS+一笔性费用+不取费定额费不含税+不取费乙供主材费不含税+不取费甲供主材费含税||四|否|100|合计|取费表||{7422B3F1-AD7B-4B33-BC19-098E6419DDC2}|
@@ -0,0 +1,47 @@
# 线路取费表(调试工程)aa_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{89584688-CE5E-459B-91CB-7EE6A67B3F69}|FFZ||撒大声地|一|否|100|直接费|取费表||{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{562076A7-DD26-454C-9551-0D4378F004E1}|FFZ1||水电费asf|1|否|100|直接工程费|取费表|{89584688-CE5E-459B-91CB-7EE6A67B3F69}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{C1F7FABF-3DD4-4143-9B50-8F77AF8CC714}|DZF||adsf|1.1|否|100|定额直接费|取费表|{562076A7-DD26-454C-9551-0D4378F004E1}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{8FFEB7C5-4BC3-4BCD-8867-3AE8D0B4AF1F}|RGF|取费定额人工费||1.1.1|否|100|人工费|取费表|{C1F7FABF-3DD4-4143-9B50-8F77AF8CC714}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{1CE55F21-2825-495D-962F-358874DF5098}|CLF|取费定额乙供材料费不含税|sdf|1.1.2|否|100|材料费|取费表|{C1F7FABF-3DD4-4143-9B50-8F77AF8CC714}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{47CCA71B-DEFA-471D-B5A9-CC572DF00E72}|JXF|取费定额机械费|dsf|1.1.3|否|100|施工机械使用费|取费表|{C1F7FABF-3DD4-4143-9B50-8F77AF8CC714}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{E4D27C6B-1830-4648-B658-3EB73FB9F68C}|ZZCF||fds|1.2|否|100|装置性材料费|取费表|{562076A7-DD26-454C-9551-0D4378F004E1}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{9C2930D6-714A-466C-B9DC-DAA94D27D6C7}|JZZCF|甲供取费主材费含税||1.2.1|否|100|甲供装置性材料费|取费表|{E4D27C6B-1830-4648-B658-3EB73FB9F68C}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{82F14392-48E0-4FF7-8F2B-656A7CFA00E7}|YZZCF|乙供取费主材费不含税|dsf|1.2.2|否|100|乙供装置性材料费|取费表|{E4D27C6B-1830-4648-B658-3EB73FB9F68C}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|FFZ2|||2|否|100|措施费|取费表|{89584688-CE5E-459B-91CB-7EE6A67B3F69}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{2E0E2997-9AB8-448D-B225-739D600B75A7}|DYF|取费定额人工费||2.1|否|3.57|冬雨季施工增加费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{C29B035D-5F92-4075-9BF1-6CA59BCE213B}|YSF|取费定额人工费|sd|2.2|否|0|夜间施工增加费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{252CA171-CC5D-4935-B1DD-DC56D611874D}|SYF|取费定额人工费|f|2.3|否|3.82|施工工具用具使用费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{9C145731-E29B-452D-B456-245B4852346B}|TDF|取费定额人工费||2.4|否|0|特殊地区施工增加费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{E52BA944-762A-4A20-964E-CB3632D72879}|LSF|DZF||2.5|否|6.35|临时设施费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{428548D1-9A8B-4278-9DDA-D393760B603D}|ZYF|取费定额人工费|dsdsf|2.6|否|2.36|施工机构迁移费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{FA0FA01C-D535-47D9-ADEE-D8FE85E9BCEE}|BZF|FFZ1-甲供主材进项税额||2.7|否|3.55|安全文明施工费|取费表|{8FA168BD-6916-49B8-A456-E8CC2A53045E}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{03647B7A-CB22-4C9D-9EC6-D31B78FE78C8}|FFJ|||二|否|100|间接费|取费表||{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{82339946-C479-4DDF-A90F-46A7E4B59B40}|GF|||1|否|100|规费|取费表|{03647B7A-CB22-4C9D-9EC6-D31B78FE78C8}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{837BB29C-A795-4761-B5CD-6D47A1222E5B}|BZHF|取费定额人工费*1.05|sdf|1.1|否|2|社会保险费|取费表|{82339946-C479-4DDF-A90F-46A7E4B59B40}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{D8947795-59A2-4B0B-81E3-1D77B5B5DACA}|GJJ|取费定额人工费*1.05||1.2|否|2|住房公积金|取费表|{82339946-C479-4DDF-A90F-46A7E4B59B40}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{DB95097F-9AAF-4B15-9A91-A60FCD5A8F8A}|GLF|取费定额人工费||2|否|35.76|企业管理费|取费表|{03647B7A-CB22-4C9D-9EC6-D31B78FE78C8}|{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{846F0E21-9BC9-4188-A699-1CF4E84D54BF}|FFR|FFZ+FFJ-甲供主材进项税额|f|三|否|5|利润|取费表||{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{F240BBFC-34FA-440E-9B9E-0185114F0668}|FFS|FFZ+FFJ+FFR-甲供取费主材费含税+不取费定额费不含税+不取费乙供主材费不含税|fsd|四|否|9|税金|取费表||{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
|{CF5E9612-3C9D-46B0-BA8F-93762C0F8131}|HJ|FFZ+FFJ+FFR+FFS+一笔性费用+不取费定额费不含税+不取费乙供主材费不含税+不取费甲供主材费含税|df|五|否|100|合计|取费表||{56791DC7-0475-4DA9-ABE6-60E32D70BAD0}|
@@ -0,0 +1,132 @@
# 线路取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{70406D96-B3AE-49BA-B01B-770DE3B90099}|FFZ||dsf|一|否|100|直接费|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{580EEFEB-BD7D-4E9E-AB6F-06112640566E}|FFZ1||dsf|1|否|100|直接工程费|取费表|{70406D96-B3AE-49BA-B01B-770DE3B90099}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{EC40FC4E-6922-49D5-A6D4-6D4DAC5D4F5D}|DZF|||1.1|否|100|定额直接费|取费表|{580EEFEB-BD7D-4E9E-AB6F-06112640566E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8D96B01B-FA07-478A-808B-C7F7173DC3E2}|RGF|取费定额人工费|sdf|1.1.1|否|100|人工费|取费表|{EC40FC4E-6922-49D5-A6D4-6D4DAC5D4F5D}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{DB5F8BD1-B3E5-492D-960B-EA429CC75B8F}|CLF|取费定额乙供材料费不含税|f|1.1.2|否|100|材料费|取费表|{EC40FC4E-6922-49D5-A6D4-6D4DAC5D4F5D}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{80157259-369F-4A43-BE1A-BAEFAA3DF543}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{EC40FC4E-6922-49D5-A6D4-6D4DAC5D4F5D}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{EC524B6C-D8E9-4B96-9F45-979A328CA242}|ZZCF||sdf|1.2|否|100|装置性材料费|取费表|{580EEFEB-BD7D-4E9E-AB6F-06112640566E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{FC50C3AD-D531-47EF-B1CC-DDC6D58B5C80}|JZZCF|甲供取费主材费含税||1.2.1|否|100|甲供装置性材料费|取费表|{EC524B6C-D8E9-4B96-9F45-979A328CA242}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{49A170B8-7B38-40F2-9392-0B79DFEFBBE2}|YZZCF|乙供取费主材费不含税|sdf|1.2.2|否|100|乙供装置性材料费|取费表|{EC524B6C-D8E9-4B96-9F45-979A328CA242}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|FFZ2||dsfs|2|否|100|措施费|取费表|{70406D96-B3AE-49BA-B01B-770DE3B90099}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{1BC0B3CD-F3DC-4501-9BBA-517247CBA843}|DYF|取费定额人工费||2.1|否|3.57|冬雨季施工增加费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{B51D7BD8-E114-495A-A331-76A9DD21310F}|YSF|取费定额人工费||2.2|否|0|夜间施工增加费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{EC9ED826-4477-4BF9-97FF-E3C7339C7345}|SYF|取费定额人工费|sdf|2.3|否|3.82|施工工具用具使用费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{0A9E4A3E-49ED-4BE1-97EC-4AD16315737C}|TDF|取费定额人工费||2.4|否|0|特殊地区施工增加费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{4A33D32F-0460-4A7E-B949-798F49318FE7}|LSF|DZF||2.5|否|6.35|临时设施费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{C19DFCF6-3036-45C3-9575-1636F532BE7D}|ZYF|取费定额人工费|sdf|2.6|否|2.36|施工机构迁移费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{5FD896CC-F364-416C-8D60-A94301EDAFA4}|BZF|FFZ1-甲供主材进项税额||2.7|否|3.55|安全文明施工费|取费表|{D69561EB-7F49-42B9-90D4-0B8F0C9F522F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8AF614D8-993D-4199-A360-8F6328D06A75}|FFJ||df|二|否|100|间接费|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{61EA8A77-BD86-41F3-8AF5-1A584B60D1DF}|GF||dsf|1|否|100|规费|取费表|{8AF614D8-993D-4199-A360-8F6328D06A75}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{7175C4E2-EEDA-428F-BA0E-8187CB6C761A}|BZHF|取费定额人工费*1.05|sd|1.1|否|2|社会保险费|取费表|{61EA8A77-BD86-41F3-8AF5-1A584B60D1DF}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{7838D12C-9489-40B1-91CE-CDE82BE01E43}|GJJ|取费定额人工费*1.05|fsdf|1.2|否|2|住房公积金|取费表|{61EA8A77-BD86-41F3-8AF5-1A584B60D1DF}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E2D542B4-0B36-4D4F-B766-829AE372D61B}|GLF|取费定额人工费||2|否|35.76|企业管理费|取费表|{8AF614D8-993D-4199-A360-8F6328D06A75}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{265EF8F8-25C1-40D5-9541-6C983203E2A4}|TSF|DZF|sdf|3|否|0|施工企业配合调试费|取费表|{8AF614D8-993D-4199-A360-8F6328D06A75}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A771C271-1AE0-4C69-A713-9A2258763A94}|FFR|FFZ+FFJ-甲供主材进项税额||三|否|5|利润|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{6D7F08B2-E8F9-46E5-AC9E-936CE7342F08}|FFS|FFZ+FFJ+FFR-甲供取费主材费含税+不取费定额费不含税+不取费乙供主材费不含税|ffsd|四|否|9|税金|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A2CB4552-ADFC-41C5-AFF3-BE3C796CAEEE}|SBF||sd|五|否|100|设备费|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{F137DC37-302F-434D-9A46-118F9B14802C}|SBY|乙供设备费不含税+乙供设备税金|fdf|1|否|100|乙供设备不含税价|取费表|{A2CB4552-ADFC-41C5-AFF3-BE3C796CAEEE}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{879B6551-1BDF-442D-B6B5-CAFF38E0CD7D}|SBJ|甲供设备费含税|sdfsd|2|否|100|甲供设备含税价|取费表|{A2CB4552-ADFC-41C5-AFF3-BE3C796CAEEE}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{078B3961-C38B-410D-A810-2AEF3E9F26FB}|AZF|DZF+FFZ2+FFJ+FFR+FFS+不取费定额费不含税+一笔性费用||六|否|100|安装费|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{329944F5-E6C9-494E-9AA8-BB59D88A3F2B}|ZCF|ZZCF+不取费乙供主材费不含税+不取费甲供主材费含税|dsf|七|否|100|主材费|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A20AEF8B-EE68-4B47-B9AA-72D30F8275A4}|ZJ|AZF+ZCF+SBF||八|否|100|总计|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{9EBA5169-2402-4BEC-8D50-AFB98EB8B3F7}|E|取费定额人工费+231|我加的|a|否|100|新费用|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{B57AEA48-C1DE-425D-A053-A585148A04B9}|HJ|ZJ-SBF+E|dsf|九|否|100|合计|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E1038F7A-CF74-40D5-90EA-586E8102768B}|||||否|100|常用变量|取费表||{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{CE1D4531-4DAB-43F0-B19C-F1B2C44B803E}||取费定额人工费||1|否|100|新费用69|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{BEC5078F-57FE-43C9-A068-FB4866499DD9}||取费定额乙供材料费不含税||2|否|100|新费用1|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{B899075D-CF02-48B5-A2A9-C82655846164}||取费定额机械费||3|否|100|新费用2|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{D63B6670-B748-4563-9C17-02E21F68BAF3}||甲供取费主材费含税||4|否|100|新费用3|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{43189C40-AA16-487F-8FC0-3B5AE33C32F8}||乙供取费主材费不含税||5|否|100|新费用4|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{20AD5254-D7E4-465A-A6B4-0EFF6741D6C2}||甲供设备费含税||6|否|100|甲供设备费含税|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{59B2E543-174A-41A2-A989-53D8C2361EEC}||乙供设备费不含税||7|否|100|乙供设备费不含税|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{0DBD69A2-F553-4289-B64F-08AAD5661492}||乙供设备税金||8|否|100|乙供设备税金|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E8A4D69C-DD16-4A5C-B249-267DA144062D}||甲供主材进项税额||9|否|100|甲供主材进项税额|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{907DCC9F-1E9D-4005-AA41-311C07D26B65}||人工价差||10|否|100|新费用5|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{67FEA6C5-9CFD-425B-A2B3-739F44BF102B}||乙供材料价差不含税||11|否|100|新费用6|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{63A8F2C0-3E19-4215-8FC1-B2C1E2EEAD8B}||机械价差||12|否|100|新费用7|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{02746A4C-4393-4FC1-BAAA-8C184695AA9F}||甲供主材价差含税||13|否|100|新费用8|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A38F7EC6-01AB-4A3E-90A7-98E49C6DBDAB}||乙供主材价差不含税||14|否|100|新费用9|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A51F720F-02CD-4B15-A688-169ABF5A973B}||不取费定额费不含税||15|否|100|新费用10|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A58A1C6B-6800-44B8-9E76-1C7C8204173D}||不取费甲供主材费含税||16|否|100|新费用11|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{72D23F7A-69FD-4B8D-B44B-974662E25BC0}||不取费乙供主材费不含税||17|否|100|新费用12|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{F0DCFFCF-7A5A-432C-832C-EA1DDDCAD41A}||工程税率||18|否|100|工程税率|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{AA4C2BC3-6749-4E19-AA38-C65A3E13FB62}||一笔性费用||19|否|100|一笔性费用|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{7476AD1B-7270-4F63-96A8-2589CF06D1B3}||线路亘长||20|否|100|线路亘长|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}||||21|否|100|新费用13|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{2F021F6F-E56D-4211-A298-9CBBBC0E0D7F}||定额_取费_人工费||21.1|否|100|新费用14|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{6CBA8586-9F1B-42A1-AADA-32CC6ED651BF}||定额_取费_乙供材料费不含税||21.2|否|100|新费用15|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{817A70A0-E8DA-44F3-8F4E-FB7E948A6FD1}||定额_取费_机械费||21.3|否|100|新费用16|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{91127133-F48B-4063-912B-BCDB7878B10E}||定额_取费_人工价差||21.4|否|100|新费用17|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{9BBC63D2-7B4D-4D48-8EB6-5A2B9BCDB3FD}||定额_取费_乙供材料价差不含税||21.5|否|100|新费用18|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{22E4FFC6-E81F-4857-9783-2FC95E1A639A}||定额_取费_机械价差||21.6|否|100|新费用19|取费表|{38FC8F6A-AA41-433E-B20E-3A4C35F0097A}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{9F894ADA-2261-4302-8BFA-386AEDF4A926}||||22|否|100|新费用20|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{927CED17-7151-4418-8FC9-B63206E283E1}||定额_不取费_人工费||22.1|否|100|新费用21|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A75FD504-21F8-4BE6-8138-9F7FF0BD0594}||定额_不取费_乙供材料费不含税||22.2|否|100|新费用22|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{03049308-7B53-4A57-8526-AC97ADBBAF47}||定额_不取费_机械费||22.3|否|100|新费用23|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{6543B15A-BF08-4045-A4B6-840BE8BB6E47}||定额_不取费_人工价差||22.4|否|100|新费用24|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{6E3F1BF6-0853-4E45-BAB4-386D524C599C}||定额_不取费_乙供材料价差不含税||22.5|否|100|新费用25|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{D59699DA-05E5-4650-88C9-8EA21BD00EFF}||定额_不取费_机械价差||22.6|否|100|新费用26|取费表|{9F894ADA-2261-4302-8BFA-386AEDF4A926}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}||||23|否|100|新费用27|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{474E7BF3-3988-44B9-AC5F-4053C3D408F0}||主材_取费_甲供主材费不含税||23.1|否|100|新费用28|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{84DB0E83-6C43-46A6-80FA-B08E8EE36E68}||主材_取费_甲供主材费含税||23.2|否|100|新费用29|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{697F88B9-9E58-49B8-AC5E-0758DEE7DFCE}||主材_取费_甲供主材损耗费不含税||23.3|否|100|新费用30|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8470F441-CAB5-4A49-B3B0-891F582ED1A9}||主材_取费_甲供主材损耗费含税||23.4|否|100|新费用31|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{B83443A8-2E42-49D9-8B73-F1FC22B7041B}||主材_取费_甲供主材价差不含税||23.5|否|100|新费用32|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{D3CCC6FE-F841-426B-A356-6BFC22D13967}||主材_取费_甲供主材价差含税||23.6|否|100|新费用33|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{15C154B4-EE35-4882-8733-C4F40E52BA95}||主材_取费_甲供主材损耗价差不含税||23.7|否|100|新费用34|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{BA607DED-D353-44EF-93AC-BAADDD1A0AB3}||主材_取费_甲供主材损耗价差含税||23.8|否|100|新费用35|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{66C0E832-4E6F-4844-9F1D-8E0A16EEDE14}||主材_取费_乙供主材费不含税||23.9|否|100|新费用36|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{9439D197-6506-4471-B3A8-1B471CFD694E}||主材_取费_乙供主材损耗费不含税||23.10|否|100|新费用37|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8F7DB6EA-CB2F-4425-8F05-0099C550EEDA}||主材_取费_乙供主材价差不含税||23.11|否|100|新费用38|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{4CDF8FA3-BED1-4556-BFBA-33F9855844DA}||主材_取费_乙供主材损耗价差不含税||23.12|否|100|新费用39|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{374EC738-5796-4708-A142-C2239C72F81C}||主材_取费_运输重量||23.13|否|100|新费用40|取费表|{D0CF04E5-2B54-4BC0-A43A-A5FEAC1F4628}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{29B550FC-E48E-4D28-A177-E4F8E484209F}||||24|否|100|新费用41|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8D0D0A30-1188-4012-B0E9-0405DE56A8B7}||主材_不取费_甲供主材费不含税||24.1|否|100|新费用42|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{EDE14BEF-1E81-4881-A214-F13026973492}||主材_不取费_甲供主材费含税||24.2|否|100|新费用43|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{4C09CF4E-81C8-4560-ABA8-FB97465FC7E9}||主材_不取费_甲供主材损耗费不含税||24.3|否|100|新费用44|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{C28704AF-43E9-4CD6-BBA0-BCF05AAEE5EA}||主材_不取费_甲供主材损耗费含税||24.4|否|100|新费用45|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{3936A573-8B9D-4CD5-8D65-BDAE63BB0D71}||主材_不取费_甲供主材价差不含税||24.5|否|100|新费用46|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{0FD66B7E-CDBC-49AF-B836-19BA85CEB858}||主材_不取费_甲供主材价差含税||24.6|否|100|新费用47|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{34514126-514F-4DF8-97E3-49C904673865}||主材_不取费_甲供主材损耗价差不含税||24.7|否|100|新费用48|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E8233277-0395-451E-AAAD-28FD938A3D6C}||主材_不取费_甲供主材损耗价差含税||24.8|否|100|新费用49|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{9AA5F7F4-4CE5-429E-8EE1-99AD32BD9677}||主材_不取费_乙供主材费不含税||24.9|否|100|新费用50|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{C154129C-4002-44C9-B994-BEB0CAA73B48}||主材_不取费_乙供主材损耗费不含税||24.10|否|100|新费用51|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{0D0C2193-1379-496D-AAC9-50754767BBEE}||主材_不取费_乙供主材价差不含税||24.11|否|100|新费用52|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8C0E8186-18E0-4AFC-B802-916495002B61}||主材_不取费_乙供主材损耗价差不含税||24.12|否|100|新费用53|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{FC1DA50B-6D72-45B4-8996-DF9E05002A64}||主材_不取费_运输重量||24.13|否|100|新费用54|取费表|{29B550FC-E48E-4D28-A177-E4F8E484209F}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{4377CDFD-A4BC-4999-9453-70E80B093C5E}||||25|否|100|新费用55|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{174A8B58-F00B-4821-8389-0847465C5EA2}||设备_普通设备_甲供设备费不含税||25.1|否|100|新费用56|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E0225E32-6C03-41F4-B99F-DF95A6CC5FD6}||设备_普通设备_甲供设备费含税||25.2|否|100|新费用57|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{E8401E26-9357-4001-8096-CE060AF515BF}||设备_普通设备_甲供设备运杂费||25.3|否|100|新费用58|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{009925CC-BD88-4C73-A775-44FF9F5E535B}||设备_普通设备_乙供设备费不含税||25.4|否|100|新费用59|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8C8D8D6A-7739-4C25-9FF7-8B5F642D8088}||设备_普通设备_乙供设备运杂费||25.5|否|100|新费用60|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{6A78CFF1-7C26-40EF-A3AD-0269B341D86E}||设备_普通设备_乙供设备税金||25.6|否|100|新费用61|取费表|{4377CDFD-A4BC-4999-9453-70E80B093C5E}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}||||26|否|100|新费用62|取费表|{E1038F7A-CF74-40D5-90EA-586E8102768B}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{41AEEC6D-CD38-486E-A240-05E21324A4E6}||设备_主要设备_甲供设备费不含税||26.1|否|100|新费用63|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{14561281-0438-4E0E-9AF9-978970E8430C}||设备_主要设备_甲供设备费含税||26.2|否|100|新费用64|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{A3EA36EA-1E6E-4E98-AE0E-C41AC66ED23D}||设备_主要设备_甲供设备运杂费||26.3|否|100|新费用65|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{DC4C6DB0-C8D7-41F8-90B4-A86C51FC5BD0}||设备_主要设备_乙供设备费不含税||26.4|否|100|新费用66|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{B26F93F7-4E62-419B-B7B9-B5A928C9B987}||设备_主要设备_乙供设备运杂费||26.5|否|100|新费用67|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
|{4BD38BC2-C975-4F2D-A2F9-4132E04AD281}||设备_主要设备_乙供设备税金||26.6|否|100|新费用68|取费表|{8294A47B-1FDF-4AAF-AAB6-CB8326F40A1C}|{0607D565-D3F4-4D42-9AB8-39C7E397C325}|
@@ -0,0 +1,32 @@
# 线路取费表(余物清理)(1)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{2EF96B62-7EFA-4E78-B2D4-EEF578970753}|FFZ||ds|一|否|100|直接费|取费表||{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{B27E7DBB-D33E-4E0C-811A-46F473455D7B}|FFZ1||sdf|1|否|100|直接工程费|取费表|{2EF96B62-7EFA-4E78-B2D4-EEF578970753}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{8E8CBA5E-E555-4DCE-830B-AE86D20BA946}|DZF|||1.1|否|100|定额直接费|取费表|{B27E7DBB-D33E-4E0C-811A-46F473455D7B}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{8ADD1F8D-AF63-4998-97CC-2E2406F3C825}|RGF|取费定额人工费|ds|1.1.1|否|100|人工费|取费表|{8E8CBA5E-E555-4DCE-830B-AE86D20BA946}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{32D2E73A-6896-4790-A019-AEA3587F5CDD}|CLF|取费定额乙供材料费不含税|ds|1.1.2|否|100|材料费|取费表|{8E8CBA5E-E555-4DCE-830B-AE86D20BA946}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{E7B8A30F-C562-474D-823A-6C27DE9F520F}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{8E8CBA5E-E555-4DCE-830B-AE86D20BA946}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{46490417-BE3A-4175-AC0A-56BD30AEDD25}|FFZ2||sdf|2|否|100|措施费|取费表|{2EF96B62-7EFA-4E78-B2D4-EEF578970753}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{4A969822-5333-43D1-A916-F6FEFF221568}|BZF|FFZ1|sdf|2.1|否|3.55|安全文明施工费|取费表|{46490417-BE3A-4175-AC0A-56BD30AEDD25}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{46B1E7CB-22F3-46E2-9438-035FC1E014F8}|W|取费定额人工费+200|我加的|2.2|否|100|新费用|取费表|{46490417-BE3A-4175-AC0A-56BD30AEDD25}|{724617D5-3F63-4FDC-962B-4FAB593C401C}|
|{C9479906-C457-49F4-B1D2-743EE0D88C48}|HJ|FFZ+一笔性费用+W|sd|二|否|100|合计|取费表||{724617D5-3F63-4FDC-962B-4FAB593C401C}|
@@ -0,0 +1,87 @@
# 线路取费表(余物清理)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{BE94FFCB-FA01-4E8B-A9B1-9FB29161E440}|FFZ||ds|一|否|100|直接费|取费表||{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{9A4DC1D7-0A24-4F41-A0E6-468F356936FA}|FFZ1||sdf|1|否|100|直接工程费|取费表|{BE94FFCB-FA01-4E8B-A9B1-9FB29161E440}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{DCC69452-0832-4D75-8716-4B1B36C34FC9}|DZF|||1.1|否|100|定额直接费|取费表|{9A4DC1D7-0A24-4F41-A0E6-468F356936FA}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{6E53A71F-235C-48D5-A738-0E68C7162743}|RGF|取费定额人工费|ds|1.1.1|否|100|人工费|取费表|{DCC69452-0832-4D75-8716-4B1B36C34FC9}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{D839833B-A862-485D-B432-90E46EBC115B}|CLF|取费定额乙供材料费不含税|ds|1.1.2|否|100|材料费|取费表|{DCC69452-0832-4D75-8716-4B1B36C34FC9}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{FCDE2FE5-2C6E-4753-82FE-7AF5BF7D2355}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{DCC69452-0832-4D75-8716-4B1B36C34FC9}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{96F0D55D-CE26-474A-8209-366CACE69262}|FFZ2||sdf|2|否|100|措施费|取费表|{BE94FFCB-FA01-4E8B-A9B1-9FB29161E440}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{35B3D950-7BD6-40B8-8637-952ED005EB33}|BZF|FFZ1|sdf|2.1|否|3.55|安全文明施工费|取费表|{96F0D55D-CE26-474A-8209-366CACE69262}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{81529EEB-96A3-4C95-807E-EAA4E9AB9927}|W|取费定额人工费|我加的|2.2|否|100|新费用|取费表|{96F0D55D-CE26-474A-8209-366CACE69262}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{EFB69F6F-0BE3-414B-BB10-A9F2C8E6CC54}|HJ|FFZ+一笔性费用+W|sd|二|否|100|合计|取费表||{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{E038685B-85A7-4A97-97DA-D3385F322B24}|||||否|100|新费用1|取费表||{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{AB265F93-20D1-49B0-9281-0FF627343E24}||||1|否|100|宏|取费表|{E038685B-85A7-4A97-97DA-D3385F322B24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{02962FEB-3A61-4B08-9F22-6B34F0ECAF1A}||取费定额人工费||1.1|否|100|新费用44|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{FF11B669-A5A5-43C8-9E7E-A8E7F60E040E}||取费定额乙供材料费不含税||1.2|否|100|新费用2|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{04E974BB-0544-4E51-9B02-6F92B522D200}||取费定额机械费||1.3|否|100|新费用3|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{A2B5BD01-A6D2-4F21-A078-A39D2B02C2D9}||甲供主材进项税额||1.4|否|100|新费用4|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{BE436CA0-0603-479D-AB5C-8B84F2EC562F}||甲供取费主材费含税||1.5|否|100|新费用5|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{0474458D-39FA-48BA-BC85-C8AFACC055C3}||乙供取费主材费不含税||1.6|否|100|新费用6|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{37BADC69-6622-49D4-9994-3926038C78B3}||不取费定额费不含税||1.7|否|100|新费用7|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{4AD79BFF-0DB0-44BB-92C9-1542E60544DB}||不取费甲供主材费含税||1.8|否|100|新费用8|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{9A450AAE-5BEB-4966-AE70-5BDD99070823}||不取费乙供主材费不含税||1.9|否|100|新费用9|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{DE20CD7C-11EB-4DC6-BB5D-F0098DA795E3}||工程税率||1.10|否|100|新费用10|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{75965A4E-E0D0-45AB-A085-60F3DE53040B}||一笔性费用||1.11|否|100|新费用11|取费表|{AB265F93-20D1-49B0-9281-0FF627343E24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{F4A7F45A-2CCD-4290-95C1-DE15B41A4FA6}||||2|否|100|基础变量|取费表|{E038685B-85A7-4A97-97DA-D3385F322B24}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{D908BF67-838A-4B86-871B-A25ED6679D8F}||||2.1|否|100|定额|取费表|{F4A7F45A-2CCD-4290-95C1-DE15B41A4FA6}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{24C1D861-C0E8-4455-A0E8-C4D105AEEF5A}||||2.1.1|否|100|取|取费表|{D908BF67-838A-4B86-871B-A25ED6679D8F}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{F79A2603-235D-40CF-BDAA-CE358A1A424B}||定额_取费_人工费||2.1.1.1|否|100|新费用12|取费表|{24C1D861-C0E8-4455-A0E8-C4D105AEEF5A}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{3244C267-E729-438D-A180-20B854D35BEB}||定额_取费_乙供材料费不含税||2.1.1.2|否|100|新费用14|取费表|{24C1D861-C0E8-4455-A0E8-C4D105AEEF5A}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{64622AE4-268D-4BD3-80E0-FCC25724AFD3}||定额_取费_机械费||2.1.1.3|否|100|新费用15|取费表|{24C1D861-C0E8-4455-A0E8-C4D105AEEF5A}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{0A5FB413-4619-40C6-B16E-97E5468C41EA}||||2.1.2|否|100|不取|取费表|{D908BF67-838A-4B86-871B-A25ED6679D8F}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{71FCC55C-EAA0-4C6C-AB18-DB45C17331BE}||定额_不取费_人工费||2.1.2.1|否|100|新费用16|取费表|{0A5FB413-4619-40C6-B16E-97E5468C41EA}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{C69006F6-A788-4976-BD02-94B7248BEA00}||定额_不取费_乙供材料费不含税||2.1.2.2|否|100|新费用13|取费表|{0A5FB413-4619-40C6-B16E-97E5468C41EA}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{91A75F8B-D3AE-42F1-9BBD-C1F7E309C0FE}||定额_不取费_机械费||2.1.2.3|否|100|新费用17|取费表|{0A5FB413-4619-40C6-B16E-97E5468C41EA}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{703BFDFD-9612-4715-B1FC-184FA1C0DBF5}||||2.2|否|100|主材|取费表|{F4A7F45A-2CCD-4290-95C1-DE15B41A4FA6}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{279825D0-1127-4C91-9EF1-10EAB9A4E321}||||2.2.1|否|100|取1|取费表|{703BFDFD-9612-4715-B1FC-184FA1C0DBF5}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{E9D9431E-6298-4AF1-86B0-F172E0283455}||主材_取费_甲供主材费不含税||2.2.1.1|否|100|新费用22|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{4D92C554-FE5B-4DB6-A582-444C7FE352A7}||主材_取费_甲供主材费含税||2.2.1.2|否|100|新费用18|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{6B5D6954-BE0F-4BF6-A6AA-34D18E4DEEC5}||主材_取费_甲供主材损耗费不含税||2.2.1.3|否|100|新费用20|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{333EE3F5-220C-454B-AA33-F74EB23EA90A}||主材_取费_甲供主材损耗费含税||2.2.1.4|否|100|新费用21|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{70CD571A-1492-448B-BEF3-D10487184E93}||主材_取费_乙供主材费不含税||2.2.1.5|否|100|新费用23|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{A205E1B1-5509-4273-8A1D-B0BD11191694}||主材_取费_乙供主材损耗费不含税||2.2.1.6|否|100|新费用24|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{7EF20055-FEB3-4BBA-803E-79860EDE7959}||主材_取费_运输重量||2.2.1.7|否|100|新费用25|取费表|{279825D0-1127-4C91-9EF1-10EAB9A4E321}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}||||2.2.2|否|100|不取1|取费表|{703BFDFD-9612-4715-B1FC-184FA1C0DBF5}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{EBC9A113-8540-43F5-8B15-E02EFA5C0771}||主材_不取费_甲供主材费不含税||2.2.2.1|否|100|新费用26|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{DE448780-63B8-4FA9-AA5D-B447DA1D726B}||主材_不取费_甲供主材费含税||2.2.2.2|否|100|新费用27|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{59A30CAA-7938-4D9F-9975-DDA8389A1876}||主材_不取费_甲供主材损耗费不含税||2.2.2.3|否|100|新费用28|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{10D2DA8F-2157-4D2A-B560-9CA42BB1D605}||主材_不取费_甲供主材损耗费含税||2.2.2.4|否|100|新费用29|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{7FEB0D34-5574-4B8C-9A2C-AD1662D276FF}||主材_不取费_乙供主材费不含税||2.2.2.5|否|100|新费用30|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{1387CE58-2FB7-4758-80A2-4F1AE59B119A}||主材_不取费_乙供主材损耗费不含税||2.2.2.6|否|100|新费用31|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{80B19A64-E375-4964-A84A-488DEEAA8F7B}||主材_不取费_运输重量||2.2.2.7|否|100|新费用32|取费表|{C83708A3-AB6A-408F-8DC4-FF286D5F6560}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{57609601-A4DB-4D54-9793-538788C8EBC8}||||2.3|否|100|设备|取费表|{F4A7F45A-2CCD-4290-95C1-DE15B41A4FA6}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}||||2.3.1|否|100|普通|取费表|{57609601-A4DB-4D54-9793-538788C8EBC8}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{CAA56A51-61FE-473F-B852-080259177EA1}||设备_普通设备_甲供设备费不含税||2.3.1.1|否|100|新费用19|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{2E449476-784A-4F1F-9930-81184FC05B9E}||设备_普通设备_甲供设备费含税||2.3.1.2|否|100|新费用33|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{17DA2ADA-91A3-46C7-AE64-C42C451EB4FD}||设备_普通设备_甲供设备运杂费||2.3.1.3|否|100|新费用34|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{E9756933-639D-4793-BBFF-671B4128D7DD}||设备_普通设备_乙供设备费不含税||2.3.1.4|否|100|新费用35|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{569A0E33-8F66-42BC-A5F4-D2D1A6065918}||设备_普通设备_乙供设备运杂费||2.3.1.5|否|100|新费用36|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{868201A0-72FF-47A1-A6CF-9297594E800D}||设备_普通设备_乙供设备税金||2.3.1.6|否|100|新费用37|取费表|{E5DE7E42-8E8B-4751-9683-E7D1C41B9D2E}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}||||2.3.2|否|100|主要|取费表|{57609601-A4DB-4D54-9793-538788C8EBC8}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{36124E58-690D-4666-B2B4-5858C5B4E048}||设备_主要设备_甲供设备费不含税||2.3.2.1|否|100|新费用38|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{0CFF5F28-C067-4652-9248-F2D35E8FC058}||设备_主要设备_甲供设备费含税||2.3.2.2|否|100|新费用39|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{4B074E2B-C3C0-4C45-AA42-3D35B88F287B}||设备_主要设备_甲供设备运杂费||2.3.2.3|否|100|新费用40|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{F6A94B03-A90C-402A-ACAB-2820F0F5DD12}||设备_主要设备_乙供设备费不含税||2.3.2.4|否|100|新费用41|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{BC11C4C8-26B7-433B-9BAC-A98F048FCCD0}||设备_主要设备_乙供设备运杂费||2.3.2.5|否|100|新费用42|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
|{3B946B5E-110C-4940-BD49-F84C22459D92}||设备_主要设备_乙供设备税金||2.3.2.6|否|100|新费用43|取费表|{6CD8B2A1-0DCC-46D1-9B28-BDE1DD6EA884}|{8C66E123-B33E-494C-8548-4E5BC456C81C}|
@@ -0,0 +1,46 @@
# 线路取费表(拆除)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{671489B1-3069-4540-8885-A4653AB1D68F}|FFZ|||一|否|100|直接费|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{34895027-670C-4027-B196-B7DD0486F08B}|FFZ1|||1|否|100|直接工程费|取费表|{671489B1-3069-4540-8885-A4653AB1D68F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{813889E2-58DD-4F32-97EB-321706FA9C34}|RGF|取费定额人工费||1.1|否|100|人工费|取费表|{34895027-670C-4027-B196-B7DD0486F08B}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{C115D7B1-0488-4879-9375-3653DCF5F720}|CLF|取费定额乙供材料费不含税||1.2|否|100|材料费|取费表|{34895027-670C-4027-B196-B7DD0486F08B}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{360CF297-ECC9-409F-8AA6-21D1D4FEFBB5}|JXF|取费定额机械费||1.3|否|100|施工机械使用费|取费表|{34895027-670C-4027-B196-B7DD0486F08B}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{681327A0-6B95-4F4A-8DC8-5415826E953F}|FFZ2|||2|否|100|措施费|取费表|{671489B1-3069-4540-8885-A4653AB1D68F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{DB8981A0-FE96-4D86-B022-3DA6E7FA1FCE}|DYF|取费定额人工费+取费定额机械费||2.1|否|1.75|冬雨季施工增加费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{F2387B8C-E709-4443-A136-9630AD483D0A}|SYF|取费定额人工费+取费定额机械费||2.2|否|0.65|施工工具用具使用费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{224DC3C6-A29D-4769-A80A-72CBD2B06FBF}|TDF|取费定额人工费+取费定额机械费||2.3|否|0|特殊地区施工增加费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{8635FAED-7F98-45C7-892A-ADEBD721DBD0}|LSF|取费定额人工费+取费定额机械费|独立的拆除工程可计取此项费,与其他工程同期实施的拆除工作不计取此项费用|2.4|否|0|临时设施费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{FC1AE4E1-5C62-410B-854C-03C181A4399D}|ZYF|取费定额人工费+取费定额机械费|独立的拆除工程可计取此项费,与其他工程同期实施的拆除工作不计取此项费用|2.5|否|0|施工机构迁移费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{83C0E923-F82E-4B4F-8000-2B43C7EF610B}|BZF|取费定额人工费+取费定额机械费||2.6|否|11.31|安全文明施工费|取费表|{681327A0-6B95-4F4A-8DC8-5415826E953F}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{D6840A86-4A8F-4385-A318-1C287A6BD78A}|FFJ|||二|否|100|间接费|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{B5488195-1AF4-499D-90A1-7DF6CC93821D}|GF|||1|否|100|规费|取费表|{D6840A86-4A8F-4385-A318-1C287A6BD78A}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{33531376-EC7C-405D-A301-00F466B84CCD}|BZHF|取费定额人工费*1.05||1.1|否|2|社会保险费|取费表|{B5488195-1AF4-499D-90A1-7DF6CC93821D}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{A0CC6D22-F031-436E-B9A6-6863C42CF19F}|GJJ|取费定额人工费*1.05||1.2|否|2|住房公积金|取费表|{B5488195-1AF4-499D-90A1-7DF6CC93821D}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{6A13E7F9-018C-4CD8-B7C8-7B883AF55486}|GLF|取费定额人工费+取费定额机械费||2|否|17.13|企业管理费|取费表|{D6840A86-4A8F-4385-A318-1C287A6BD78A}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{B31A2F7E-81E9-4F8A-A5B2-DB434834D726}|FFR|取费定额人工费+取费定额机械费||三|否|5.24|利润|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{11573E7B-EDF3-4D90-B232-EBC01F7829E2}|JC|||四|否|100|编制基准期价差|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{9569B2B2-35C3-4ACC-A38A-B5392F9D3536}|RJC|人工价差||1|否|100|人工价差|取费表|{11573E7B-EDF3-4D90-B232-EBC01F7829E2}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{BE8609FF-EE14-4C77-AE90-052F935E4ED2}|CJC|乙供材料价差不含税||2|否|100|材料价差|取费表|{11573E7B-EDF3-4D90-B232-EBC01F7829E2}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{AB75B0DE-89D4-4234-AE2F-9D167B0E5C01}|JJC|机械价差||3|否|100|机械价差|取费表|{11573E7B-EDF3-4D90-B232-EBC01F7829E2}|{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{098FBD97-2A3D-4CBB-B143-474B78A2B86E}|FFS|FFZ+FFJ+FFR+JC+不取费定额费不含税||五|否|9|税金|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
|{74E7A256-2564-49FE-8251-357AED61E082}|HJ|FFZ+FFJ+FFR+FFS+JC+一笔性费用+不取费定额费不含税||六|否|100|合计|取费表||{0A3B35A0-1B83-4A73-8677-3A436225DCCE}|
@@ -0,0 +1,217 @@
# 工程属性
备注:工程属性表是用于存储整个工程的重要属性,访问该表都是为了通过属性名查找属性值。通常属性值有工程信息、工程属性、技经参数,表中包含工程总投资、工程总费用,工程主要费用,工程技经参数等。查询示例: SELECT Value FROM ProjectProperties WHERE Name = 'findname'。
- 字段名称:名称
- 字段名称:值
- 备注:属性值,值、变量值、参数值、数值
|名称|值|
|---|---|
|设置线材工地运输计算方式|按实际用量计算|
|材料调差系数|-0.95|
|拆除安装材料按系数调差|1|
|甲供材料损耗是否计入甲供材料费|-1|
|计税方式|增值税|
|地形调整及跳跃施工计算顺序|0|
|是否自动计算凿桩头总量|是|
|脚手架材料费系数|0.5|
|是否首次统计工程量||
|云端同步|False|
|线路清单组件库|线路组件库(2018版).zjzjk|
|固定综合单价模式||
|总价万元|77469835.590045|
|建筑工程按系数调差|0|
|QtyID|21211|
|发布版工程量清单||
|材机是否按系数调差|1|
|材机界面是否只显示新增资源|FALSE|
|工程唯一标识码|{2FD2000A-C003-4573-8605-88C7B94EFA0F}|
|计价方式|定额计价|
|升级历史|1.2.0.111;1.3.0.65;1.3.3.4;1.4.0.72;1.4.1.61;1.4.2.14;1.5.0.6;1.5.1.112;1.5.2.7;1.6.0.73;1.6.1.67;2.0.0.98;2.0.1.6;2.1.0.61;2.1.0.175;2.2.1.2;2.3.0.83;2.3.1.5;2.3.4.3;2.4.0.124;2.4.1.4;2.4.3.3;2.4.4.5;2.5.0.155;2.5.1.14;2.6.0.218;2.6.2.0;2.6.3.0;2.7.0.0;2.8.0.0;3.0.0.0;3.0.1.0;3.1.0.0;3.1.1.0;3.1.2.0;3.1.2.0;|
|配置选项|DL/T 54xx导则|
|工程税率|9|
|取费表显示级别|项目划分级别显示|
|投标人||
|是否第一次打开工程||
|安装人工按系数调差|1|
|是否按单位控制工程量精度|否|
|安装材料按系数调差|1|
|工程阶段||
|脚手架费率|5|
|市场价唯一|是|
|耐张、转角塔导线挂线是否计算综合地形增加费|0|
|地方规范||
|默认自定义拆除定额库|自定义拆除定额库|
|项目类型|架空输电线路工程|
|工程文件预览信息|●工程名称:架线南网●项目划分:架空输电线路工程●工程阶段:可行性研究投资估算●地区类型:Ⅰ类●工程所在地:上海●执行规范:南网规约2018年版●工程版本:3.1.2.0●升级历史:1.2.0.111;1.3.0.65;1.3.3.4;1.4.0.72;1.4.1.61;1.4.2.14;1.5.0.6;1.5.1.112;1.5.2.7;1.6.0.73;1.6.1.67;2.0.0.98;2.0.1.6;2.1.0.61;2.1.0.175;2.2.1.2;2.3.0.83;2.3.1.5;2.3.4.3;2.4.0.124;2.4.1.4;2.4.3.3;2.4.4.5;2.5.0.155;2.5.1.14;2.6.0.218;2.6.2.0;2.6.3.0;2.7.0.0;2.8.0.0;3.0.0.0;3.0.1.0;3.1.0.0;3.1.1.0;3.1.2.0;3.1.2.0;●加密属性:|
|甲供材料计入综合单价||
|工程所在地|上海|
|岩石灌浆基础超灌量|8|
|阶段类型|概预算|
|评审费_架线长度||
|余土外运量|583624.490963|
|评审费_回路类型||
|脚手架人工费系数|0.4|
|是否开放组件统计|是|
|工程总投资|71503585.3336|
|清单规范|2014版|
|灌注桩超灌量|17|
|线路定额统计规则库|线路定额统计规则(2018版).bwgzk6|
|物料增值税率|13|
|工程创建模板|南网规约|
|国网14升21||
|编制单位|qwe|
|定额价目本|2006|
|加密属性||
|费用对比类型||
|默认清单组价方式||
|甲供材料是否计取税金||
|导入发布版工程量清单||
|机械调差系数|-0.95|
|拆除安装工程默认定额库|拆除预算 第三册 架空线路工程|
|建筑项目划分代码前缀|BT|
|脚手架计算基数|人工费|
|配合比拆分||
|报表类型|预算报表|
|泥沼地形比例|0|
|平地地形比例|0|
|BCL版本|3.1.0|
|材料单公里用量计算规则|按线路亘长计算|
|工程按系数调差|1|
|专业扩展类型||
|工程编号|qwe|
|工程改造性质|新建|
|是否组合件库||
|基本预备费费率|2|
|工程默认人材机库||
|是否设置岩石坑排水||
|发布版本|0|
|专业类型|送电|
|相同清单合并|是(清单属性及工程量一致)|
|拆除材料调差系数|9.89|
|标准清单编码长度|3|
|特殊地区|常规地区|
|塔材代用部分是否计入主材费||
|拆除安装人工按系数调差|1|
|规划台数||
|安装工程默认定额库|预算 第四册 架空输电线路工程(2018年版)|
|线路工程安全文明施工费||
|安装其他设备运杂费率||
|默认自定义主材库|自定义材料库|
|安装工程量是否首次统计工程量|否|
|预算转清单||
|工程有效性数据|Sz4OdABix8AovWI1BEEUBgBntq9R0RQwHUl8cQRnw8RTqRRBdQUVAwdkwbAppWU3Bw==|
|物料价格联动|否|
|评审费_电压等级||
|拆除建筑人工按系数调差|1|
|安装机械按系数调差|1|
|拆除建筑材料按系数调差|0|
|启用自定义安全文明施工费||
|建筑工程默认定额库|预算 第五册 电缆输电线路工程(2018年版)|
|组件参数汇总错误||
|工程只读密码||
|打开工程是否需要刷新招标人信息||
|默认自定义设备库|自定义设备库|
|工程调差文件|调差系数文件〔2020年14号文〕|
|监理费计算依据|预规(2018版)|
|工程构成类型||
|山地地形比例|0|
|塔基占地面积|4218.965188|
|高山地形比例|0|
|工资津贴补差|0.89|
|安装工程默认清单库|送电线路清单库(2014)|
|工程默认主材库|装置性材料预算价2018|
|录入工程量标记招||
|工程名称|架线南网|
|组价方式|综合单价|
|工程深度||
|工程造价咨询法定代表人或其授权人||
|措施规费按清单级取费|1|
|编制人|qwe|
|是否为特高压工程||
|组合件模式||
|安装工程默认规则库|线路典型清单库|
|工程总投资(万元)|81579073.299588|
|塔材以大代小|3|
|商品砼预算价||
|工程默认设备库||
|建筑工程默认清单库||
|建筑人工按系数调差|1|
|区域类型|国网清单工程|
|表头设置|估算|
|工程模式||
|钻孔爆扩基础超灌量|7|
|所区占地面积||
|项目划分面板数据加载||
|插件名称|南网规约插件|
|建筑工程默认规则库||
|架线长度|5|
|默认自定义定额库|自定义定额库|
|人工调差系数|4.05|
|工程地址|qwe|
|是否生成数据|0|
|调差系数设置默认地区类型|Ⅰ类 地区|
|地方清单规范||
|拆除机械调差系数|9.89|
|本期单台容量||
|工程默认调试库||
|塔材代用部分是否自动计算安装费|0|
|隐藏中标数据||
|安装项目划分代码前缀|BA|
|空表显示状态|显示空表|
|工程建筑面积||
|线路清单统计规则库|线路清单统计规则(2014版清单规范).bwqdk6|
|招标控制价导造价接口||
|默认自定义清单库|自定义清单库(2014)|
|本期台数||
|标段||
|中介机构法定(授权)代表人||
|SID|5100|
|丘陵地形比例|0|
|架线合并方案预算类型||
|拆除安装机械按系数调差|1|
|编制时间|2020-10-9|
|工程密码||
|执行规范|南网规约2018年版|
|脚手架机械费系数|0.1|
|拆除建筑机械按系数调差|0|
|预算类型|可行性研究投资估算|
|工程描述||
|建筑消材应用调差范围|FALSE|
|关联造价工程id||
|招标人||
|现浇护壁超灌量|17|
|脚手架人工工日系数|0.4|
|规划单台容量||
|拆除工程调差文件|2024年上半年调差系数文件(28号文)|
|住房公积金费率|2|
|不同土质定额归属不同清单|是|
|工程版本|3.1.2.4|
|默认组件库|线路组件库(2014版清单规范)|
|一笔性施工企业配合调试费|0|
|峻岭地形比例|0|
|软件名称|博微电力建设计价通软件|
|电压等级|35kV|
|冷却方式||
|资质证书|qwe|
|本期容量||
|掏挖基础超灌量|7|
|地区类型|Ⅰ类|
|招标法定代表人或其授权人||
|编辑时间||
|工程类型|可行性研究投资估算|
|定额版本||
|架线类型|一般线路|
|社会保险费费率|2|
|工程历史版本列表||
|2.3.4升级工程||
|显示全部数据||
|线路清理项目安全文明施工费||
|机械台班拆分||
|线路项目划分代码前缀|BA|
|工程造价咨询人||
|只读||
|拆除人工调差系数|11.03|
|拆分材料人工是否调差|是|
|导入工程量清单||
|是否重算费用||
|拆除工程材机按系数调差|0|
@@ -0,0 +1,80 @@
# 总算表
备注:总算表也被称为“工程总费用”、“工程费用”。其中包含本地工程、辅助设施工程、编制基准期价差、设备购置费、其他费用、基本预备费、特殊费用、工程静态投资、动态费用、价差预备费、建设期贷款利息、工程动态投资、可抵扣增值税额。查询示例: SELECT Amount FROM TotalCalculateTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:nodeType
- 字段名称:relTbId
- 字段名称:parentId
- 字段名称:序号
- 备注:序号
- 字段名称:名称
- 备注:项目名,费用名,名称
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:金额_单位投资,合计投资金额
- 字段名称:取费基数
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:金额
- 备注:金额_设备费,设备价格,设备金额
- 字段名称:编码
- 备注:WBS编号,WBS编码
- 字段名称:服务内容
- 字段名称:费用归属
- 字段名称:输出
- 字段名称:不可竞争费用
- 字段名称:编制依据
- 字段名称:备注
- 字段名称:表一显示
- 字段名称:建筑费
- 字段名称:安装费
- 备注:安装金额,安装价格,金额_安装费
- 字段名称:设备费
- 备注:金额_设备费,设备价格,设备金额
- 字段名称:其他费
- 备注:其他费用金额,其他费用价格,金额_其他费
- 字段名称:合计费
- 备注:金额,价格
- 字段名称:占总计
- 备注:总体金额,总的金额,金额_占总计
- 字段名称:单位投资
- 备注:金额_单位投资,合计投资金额
- 字段名称:建安合计费
- 字段名称:金额增减
|_id|nodeType|relTbId|parentId|序号|名称|代码|单位|取费基数|费率|金额|编码|服务内容|费用归属|输出|不可竞争费用|编制依据|备注|表一显示|建筑费|安装费|设备费|其他费|合计费|占总计|单位投资|建安合计费|金额增减|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|31ywrqpe70g0|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||一|架空输电线路本体工程|BTGC|%||100|55105688268.517624|2131243|||是|否|||否|0|55105688268.517624|0|0|55105688268.517624|7.706703|11021137653.703526|0|55105688268.517624|
|31ywrqpgowsg|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqpe70g0|(一)|一般线路本体工程|XLBT|%||100|55105688268.517624|wre34|||是|否|||否|0|55105688268.517624|0|0|55105688268.517624|7.706703|11021137653.703526|0|55105688268.517624|
|31ywrqpgowsh|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||二|辅助设施工程|FZSS|%||100|403152254301.795654|234|||是|否|||否|0|0|0|403152254301.795654|403152254301.795654|56.382103|80630450860.359131|0|403152254301.795654|
|31ywrqpj6t4w|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|||小计|HJ|元||100|458257942570.313293|324|||是|否|||否|0|55105688268.517624|0|403152254301.795654|458257942570.313293|64.088806|91651588514.062653|0|458257942570.313293|
|31ywrqplophc|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||三|编制基准期价差|JC|元||100|29246752707.118019|31840000000|||是|否|||否|0|29246752707.118019|0|0|29246752707.118019|4.09025|5849350541.423603|0|29246752707.118019|
|31ywrqplophd|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||四|设备购置费|SBGZF|元||100|2567934636.357451|318A0000000|||是|否|||否|0|0|2567934636.357451|0|2567934636.357451|0.359134|513586927.27149|0|2567934636.357451|
|31ywrqpo6lts|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||五|其他费用|QTFY|元||100|210942912572.869415|31830000000|||是|否|||否|0|0|0|210942912572.869415|210942912572.869415|29.501026|1231231|0|210942912572.869415|
|31ywrqpqoi68|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqpo6lts|1|其中:建设场地征用及清理费||%||100|16831284.228711|23|||是|否|||否|0|0|0|16831284.228711|16831284.228711|0|123|0|16831284.228711|
|31ywrqpqoi69|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqpo6lts|2|其中:工程建设检测费||||100|185575370.146398||||否|否|||否|0|0|0|185575370.146398|185575370.146398|0|0|0|185575370.146398|
|31ywrqpt6eio|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqpo6lts|3|其中:特种设备安全监测费||||100|0||||否|否|||否|0|0|0|0|0|0|0|0|0|
|31ywrqpvoav4|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqpo6lts|4|其中:水土保持监测及验收费||||100|0||||否|否|||否|0|0|0|0|0|0|0|0|0|
|31ywrqpvoav5|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||六|基本预备费|JBYBF|%||100|14020310849.733164|318D0000000|||是|否|||否|0|0|0|14020310849.733164|14020310849.733164|1.960784|2804062169.946633|0|14020310849.733164|
|31ywrqpy677k|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||七|特殊项目|TSXM|%||100|0|31850000000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ywrqpy677l|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|||工程静态投资|JTTZ|元||100|715035853336.391357|31860000000|||是|否|||否|0|84352440975.635651|2567934636.357451|628115477724.398193|715035853336.391357|100|2312312|0|715035853336.391357|
|31ywrqq0o3k0|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||八|动态费用|DTFY|元||100|61246155757.175179|31870000000|||是|否|||否|0|0|0|61246155757.175179|61246155757.175179|0|0|0|61246155757.175179|
|31ywrqq35zwg|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq0o3k0|(一)|价差预备费|JCYBF|元||100|22731130869.665558|31871000000|||是|否|||否|0|0|0|22731130869.665558|22731130869.665558|0|0|0|22731130869.665558|
|31ywrqq35zwh|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq0o3k0|(二)|建设期贷款利息|DKLX|元||100|38515024887.509613|31872000000|||是|否|||否|0|0|0|38515024887.509613|38515024887.509613|0|0|0|38515024887.509613|
|31ywrqq5nw8w|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|||工程动态投资|DTTZ|元||100|776282009093.566406|318C0000000|||是|否|||否|0|84352440975.635651|2567934636.357451|689361633481.573364|776282009093.566406|0|155256401818.713287|0|776282009093.566406|
|31ywrqq5nw8x|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|||其中:可抵扣增值税额|ZZS|%||100|20069645492.28894|318G0000000|||是|否|||否|0|18713773821.487453|321303868.972724|1034567801.828762|20069645492.28894|0|0|0|20069645492.28894|
|31ywrqq85slc|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}||12|常用变量||||100|0||||否|否|||否|0|782331434488.350952|0|0|0|0|0|0|0|
|31ywrqqanoxs|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.1|本体工程费||||100|0||||否|否|||否|0|55105688268.517624|0|0|0|0|0|0|0|
|31ywrqqd5la8|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.2|设备购置费1||||100|0||||否|否|||否|0|2567934636.357451|0|0|0|0|0|0|0|
|31ywrqqd5la9|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.3|常用变量:建设期贷款利息||||100|0||||否|否|||否|0|38515024887.509613|0|0|0|0|0|0|0|
|31ywrqqfnhmo|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.4|编制基准期价差1||||100|0||||否|否|||否|0|29246752707.118019|0|0|0|0|0|0|0|
|31ywrqqfnhmp|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.5|余物清理费||||100|0||||否|否|||否|0|90736.228711|0|0|0|0|0|0|0|
|31ywrqqi5dz4|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.6|常用变量:价差预备费||||100|0||||否|否|||否|0|22731130869.665558|0|0|0|0|0|0|0|
|31ywrqqi5dz5|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.7|常用变量:其他费用||||100|0||||否|否|||否|0|210942912572.869415|0|0|0|0|0|0|0|
|31ywrqqknabk|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.8|辅助费用||||100|0||||否|否|||否|0|403152254301.795654|0|0|0|0|0|0|0|
|31ywrqqn56o0|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.9|工程税率||||100|0||||否|否|||否|0|9|0|0|0|0|0|0|0|
|31ywrqqpn30g|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.10|基本预备费费率||||100|0||||否|否|||否|0|2|0|0|0|0|0|0|0|
|31ywrqqs4zcw|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.11|本体工程可抵扣增值税||||100|0||||否|否|||否|0|18713773821.487453|0|0|0|0|0|0|0|
|31ywrqqs4zcx|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.12|设备可抵扣增值税||||100|0||||否|否|||否|0|321303868.972724|0|0|0|0|0|0|0|
|31ywrqqumvpc|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.13|其他费用可抵扣增值税||||100|0||||否|否|||否|0|1034567801.828762|0|0|0|0|0|0|0|
|31ywrqqumvpd|总算表|{64B460A2-03EB-4408-8CA0-374CA991DF43}|31ywrqq85slc|12.14|线路亘长||||100|0||||否|否|||否|0|5|0|0|0|0|0|0|0|
@@ -0,0 +1,68 @@
# 项目划分_余物清理
备注:项目划分表是用于存储工程项目划分树状数据。内部包含安装工程项目划分,建筑工程项目划分,线路项目划分,工程分部分项。查询示例: SELECT Sum_Price FROM ProjectDivision WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:专业类型
- 备注:专业类型
- 字段名称:人工调差系数
- 备注:拆除人工调差系数
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:单位
- 字段名称:取费表
- 备注:取费表
- 字段名称:合价
- 备注:合价,合计
- 字段名称:名称
- 备注:项目名,名称
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:项目序号,序号,序列号
- 字段名称:拆除人工调差系数
- 备注:拆除人工调差系数
- 字段名称:拆除机械调差系数
- 备注:拆除机械调差系数
- 字段名称:拆除材料调差系数
- 备注:拆除材料调差系数
- 字段名称:数量
- 备注:数目,数量,个数
- 字段名称:机械调差系数
- 备注:拆除机械调差系数
- 字段名称:材料调差系数
- 备注:拆除材料调差系数
- 字段名称:编码
- 备注:译码,编码
- 字段名称:计算式
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用编码
- 字段名称:路径
- 备注:路径,项目全路径
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|专业类型|人工调差系数|代码|单位|取费表|合价|名称|备注|序号|拆除人工调差系数|拆除机械调差系数|拆除材料调差系数|数量|机械调差系数|材料调差系数|编码|计算式|费率|费用编码|路径|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|余物清理|0||||25411.279078|建筑工程||1|0|0|0||0|0|01||0||建筑工程|项目划分||{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{B5FA19AC-8E12-4E61-AB42-DC422074DDC7}|余物清理|0|||线路取费表(余物清理)|8443.759693|一般砖木结构||1.1|0|0|0||0|0|0101||10||建筑工程/一般砖木结构|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{6B94B24B-5CF9-4357-B6C4-46F001C329C2}|余物清理|0||||16967.519385|混合结构||1.2|0|0|0||0|0|0102||20||建筑工程/混合结构|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{8ED2CCC2-89B9-443D-9D80-34C5F395495D}|余物清理|0|W1|kW.h|线路取费表(余物清理)(1)|16967.519385|新增项目名称||1.2.1|0|0|0|12|0|0|010201|12|20||建筑工程/混合结构/新增项目名称|项目划分|{6B94B24B-5CF9-4357-B6C4-46F001C329C2}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{3E734273-05F0-464F-9F50-39BE60D1372B}|余物清理|0||||0|混凝土及钢筋混凝土结构||1.3|0|0|0||0|0|0103||0||建筑工程/混凝土及钢筋混凝土结构|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{033FC9AC-4E41-427E-9955-84CF77645793}|余物清理|0|||线路取费表(余物清理)|0|(1)有条件爆破的||1.3.1|0|0|0||0|0|010301||20||建筑工程/混凝土及钢筋混凝土结构/(1)有条件爆破的|项目划分|{3E734273-05F0-464F-9F50-39BE60D1372B}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{8F59E581-3BA2-4BE8-8BB7-8A3DF6DD4B28}|余物清理|0|||线路取费表(余物清理)|0|(2)无条件爆破的|费率在30~50区间|1.3.2|0|0|0||0|0|010302||0||建筑工程/混凝土及钢筋混凝土结构/(2)无条件爆破的|项目划分|{3E734273-05F0-464F-9F50-39BE60D1372B}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{8FC91011-52C1-4D5E-9F32-E1E38956A945}|余物清理|0|||线路取费表(余物清理)|0|临时简易建筑||1.4|0|0|0||0|0|0104||8||建筑工程/临时简易建筑|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{A9E59E43-8152-4DD7-B28F-C4FA2DAE52F7}|余物清理|0||||0|金属结构||1.5|0|0|0||0|0|0105||0||建筑工程/金属结构|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{8C214973-0FA1-46CC-9515-D593F82087E9}|余物清理|0|||线路取费表(余物清理)|0|(1)拆除后能利用||1.5.1|0|0|0||0|0|010501||55||建筑工程/金属结构/(1)拆除后能利用|项目划分|{A9E59E43-8152-4DD7-B28F-C4FA2DAE52F7}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{2E846DB0-2E2F-47DA-8577-D6C61E24C2D9}|余物清理|0|||线路取费表(余物清理)|0|(2)拆除后不能利用||1.5.2|0|0|0||0|0|010502||38||建筑工程/金属结构/(2)拆除后不能利用|项目划分|{A9E59E43-8152-4DD7-B28F-C4FA2DAE52F7}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{7D31B891-834D-40D4-BBCF-ED5B5576AE7D}|余物清理|0|||线路取费表(余物清理)|0|新增项目名称||1.6|0|0|0||0|0|0106||0||建筑工程/新增项目名称|项目划分|{B562B2D7-2C6D-4A15-BF4F-CC58EA00EA9A}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{1214A9EF-CF72-40BF-B565-F6BA007EAE44}|余物清理|0||||65324.949633|安装工程||2|0|0|0||0|0|02||0||安装工程|项目划分||{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{CACFA684-07BD-4C73-9029-8E6BCCBBD044}|余物清理|0|||线路取费表(余物清理)(1)|38176.918617|金属结构及工业管道||2.1|0|0|0||0|0|0201||45||安装工程/金属结构及工业管道|项目划分|{1214A9EF-CF72-40BF-B565-F6BA007EAE44}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{C408C657-9B4E-4519-BF3C-DAE9A9AA3B18}|余物清理|0||||27148.031016|机电设备||2.2|0|0|0||0|0|0202||32||安装工程/机电设备|项目划分|{1214A9EF-CF72-40BF-B565-F6BA007EAE44}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{9490E5FB-D00A-4BFE-AECC-7DF5E1D5C0A8}|余物清理|0||km|线路取费表(余物清理)(1)|27148.031016|新增项目名称||2.2.1|0|0|0|2|0|0|020201|2|32||安装工程/机电设备/新增项目名称|项目划分|{C408C657-9B4E-4519-BF3C-DAE9A9AA3B18}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{7E874CEB-D21D-4300-ACEA-CF993E269E77}|余物清理|0||||0|输电线路及通信线路||2.3|0|0|0||0|0|0203||0||安装工程/输电线路及通信线路|项目划分|{1214A9EF-CF72-40BF-B565-F6BA007EAE44}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{DD1578AD-E370-40A6-8659-09F8E7B2E948}|余物清理|0|||线路取费表(余物清理)|0|(1)拆除后能利用||2.3.1|0|0|0||0|0|020301||62||安装工程/输电线路及通信线路/(1)拆除后能利用|项目划分|{7E874CEB-D21D-4300-ACEA-CF993E269E77}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{120A2784-65E6-477A-BF99-F76A4E0048ED}|余物清理|0|||线路取费表(余物清理)|0|(2)拆除后不能利用||2.3.2|0|0|0||0|0|020302||35||安装工程/输电线路及通信线路/(2)拆除后不能利用|项目划分|{7E874CEB-D21D-4300-ACEA-CF993E269E77}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
|{586F768E-99D7-4A72-A453-C2471841C91F}|余物清理|0|||线路取费表(余物清理)|0|新增项目名称||2.4|0|0|0||0|0|0204||0||安装工程/新增项目名称|项目划分|{1214A9EF-CF72-40BF-B565-F6BA007EAE44}|{4C10E00C-A42E-47DA-8877-C2698F5B351B}|
@@ -0,0 +1,96 @@
# 项目划分_线路
备注:项目划分表是用于存储工程项目划分树状数据。内部包含安装工程项目划分,建筑工程项目划分,线路项目划分,工程分部分项。查询示例: SELECT Sum_Price FROM ProjectDivision WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:专业类型
- 备注:专业类型
- 字段名称:人工调差系数
- 备注:拆除人工调差系数
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:单位
- 字段名称:取费表
- 备注:取费表
- 字段名称:合价
- 备注:合价,合计
- 字段名称:名称
- 备注:项目名,名称
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:项目序号,序号,序列号
- 字段名称:拆除人工调差系数
- 备注:拆除人工调差系数
- 字段名称:拆除机械调差系数
- 备注:拆除机械调差系数
- 字段名称:拆除材料调差系数
- 备注:拆除材料调差系数
- 字段名称:数量
- 备注:数目,数量,个数
- 字段名称:机械调差系数
- 备注:拆除机械调差系数
- 字段名称:材料调差系数
- 备注:拆除材料调差系数
- 字段名称:编码
- 备注:译码,编码
- 字段名称:计算式
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用编码
- 字段名称:路径
- 备注:路径,项目全路径
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|专业类型|人工调差系数|代码|单位|取费表|合价|名称|备注|序号|拆除人工调差系数|拆除机械调差系数|拆除材料调差系数|数量|机械调差系数|材料调差系数|编码|计算式|费率|费用编码|路径|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|线路|4.05|BTGC|元/km||55105688268.517624|一般线路本体工程||一|11.03|9.89|9.89||-0.95|-0.95|||0|Y1820000000|一般线路本体工程|项目划分||{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4CC653B1-9AB2-4452-82C2-08194128B670}|线路|4.05|JCGC|元/m³||49051649642.966728|基础工程||1|11.03|9.89|9.89|3|-0.95|-0.95||3|0|Y1821000000|一般线路本体工程/基础工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{CB397026-AA60-41AB-AA61-A4FA19B4820B}|线路|4.05||km|线路取费表|15878388617.141884|基础工程材料工地运输||1.1|11.03|9.89|9.89|3|-0.95|-0.95||3|0|Y1821100000|一般线路本体工程/基础工程/基础工程材料工地运输|项目划分|{4CC653B1-9AB2-4452-82C2-08194128B670}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{648EDE70-DCAC-4A48-99BD-17B6AE7EB9F1}|线路|4.05|||线路取费表(调试工程)aa|32872843180.742939|基础土石方工程||1.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821200000|一般线路本体工程/基础工程/基础土石方工程|项目划分|{4CC653B1-9AB2-4452-82C2-08194128B670}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|线路|4.05||kW.h||299086175.656503|基础砌筑||1.3|11.03|9.89|9.89|3|-0.95|-0.95||3|0|Y1821300000|一般线路本体工程/基础工程/基础砌筑|项目划分|{4CC653B1-9AB2-4452-82C2-08194128B670}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4DB0D97A-7C4B-4A05-8C65-3BE37D206FCE}|线路|4.05|||线路取费表|40567.263948|预制基础||1.3.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821301000|一般线路本体工程/基础工程/基础砌筑/预制基础|项目划分|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4DA9BF14-1718-4C43-B6C8-062E69E78EC4}|线路|4.05||工日|大型土石方取费表|236394313.672133|现浇基础||1.3.2|11.03|9.89|9.89|3|-0.95|-0.95||3|0|Y1821302000|一般线路本体工程/基础工程/基础砌筑/现浇基础|项目划分|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{12640B7F-A48C-4365-BCC8-45E13AA8DCF9}|线路|4.05|||线路取费表|43466660.054439|灌注桩基础||1.3.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821303000|一般线路本体工程/基础工程/基础砌筑/灌注桩基础|项目划分|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{3083FEBE-7B05-46B2-A2C7-01B00809B2D5}|线路|4.05|||线路取费表|15344967.900295|锚杆基础|综合地形增加费|1.3.4|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821304000|一般线路本体工程/基础工程/基础砌筑/锚杆基础|项目划分|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{EB0DF736-2367-4142-A72E-2F9DF0E6D08D}|线路|4.05|||线路取费表|3839666.765688|其他基础||1.3.5|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821305000|一般线路本体工程/基础工程/基础砌筑/其他基础|项目划分|{B58BE3AE-DC2D-4731-B5BB-9C703081C3F3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{DDFE825A-2FFE-4FB6-A949-211780B90F5A}|线路|4.05|||线路取费表|1331669.425409|基础防护||1.4|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821400000|一般线路本体工程/基础工程/基础防护|项目划分|{4CC653B1-9AB2-4452-82C2-08194128B670}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{BE86FD67-2F31-4904-B277-32E55FF547E9}|线路|4.05|||线路取费表|0|地基处理||1.5|11.03|9.89|9.89||-0.95|-0.95|||0|Y1821500000|一般线路本体工程/基础工程/地基处理|项目划分|{4CC653B1-9AB2-4452-82C2-08194128B670}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{F02F91A2-A66B-46B3-8F4D-2C5148B94B4C}|线路|4.05||t|线路取费表|40620.619487|新增项目名称||2|11.03|9.89|9.89|3|-0.95|-0.95||3|0||一般线路本体工程/新增项目名称|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{1D83EABA-B0D9-403C-AE85-33A293EF198E}|线路|4.05|GTGC|元/t||220969744.905856|杆塔工程||3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1822000000|一般线路本体工程/杆塔工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{69D6C707-742E-4A5A-BA63-8C6EAFF1AAD9}|线路|4.05||m³|线路取费表(调试工程)aa|218715838.819873|杆塔工程材料工地运输||3.1|11.03|9.89|9.89|32|-0.95|-0.95||32|0|Y1822100000|一般线路本体工程/杆塔工程/杆塔工程材料工地运输|项目划分|{1D83EABA-B0D9-403C-AE85-33A293EF198E}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{48A176DF-97A9-4670-A525-0FDEF2E32BC2}|线路|4.05||||2253906.085983|杆塔组立||3.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1822200000|一般线路本体工程/杆塔工程/杆塔组立|项目划分|{1D83EABA-B0D9-403C-AE85-33A293EF198E}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{38276E0A-6DC1-40DA-8374-FDC8C1D47650}|线路|4.05||g|大型土石方取费表|23686.405216|混凝土杆组立|12|3.2.1|11.03|9.89|9.89|2|-0.95|-0.95||2|0|Y1822201000|一般线路本体工程/杆塔工程/杆塔组立/混凝土杆组立|项目划分|{48A176DF-97A9-4670-A525-0FDEF2E32BC2}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{CABA2E98-ED97-456D-B9A4-0B3C068FB45E}|线路|4.05|||线路取费表|2230219.680767|铁塔、钢管杆组立||3.2.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1822202000|一般线路本体工程/杆塔工程/杆塔组立/铁塔、钢管杆组立|项目划分|{48A176DF-97A9-4670-A525-0FDEF2E32BC2}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{7A747F1A-78CE-4F89-8B20-C5F9448BA814}|线路|4.05|JDGC|元/基||121964.914965|接地工程||4|11.03|9.89|9.89||-0.95|-0.95|||0|Y1823000000|一般线路本体工程/接地工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{2A31D241-CBDE-4F85-AE67-7A7120308C53}|线路|4.05|||线路取费表|97182.716229|接地工程材料工地运输||4.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1823100000|一般线路本体工程/接地工程/接地工程材料工地运输|项目划分|{7A747F1A-78CE-4F89-8B20-C5F9448BA814}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{18ACAFE5-D0A9-4DDF-9AE7-5E8AA3E56690}|线路|4.05|||线路取费表|18199.265199|接地土石方||4.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1823200000|一般线路本体工程/接地工程/接地土石方|项目划分|{7A747F1A-78CE-4F89-8B20-C5F9448BA814}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{136AA0F5-BCF2-4933-BDF9-79E5866728EC}|线路|4.05|||线路取费表|6582.933537|接地安装||4.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1823300000|一般线路本体工程/接地工程/接地安装|项目划分|{7A747F1A-78CE-4F89-8B20-C5F9448BA814}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{A000AD2A-24D9-49BC-B3E0-0303E2CF6988}|线路|4.05|JXGC|元/km||4844399648.077858|架线工程||5|11.03|9.89|9.89||-0.95|-0.95|||0|Y1824000000|一般线路本体工程/架线工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{9CE13DFF-A7D7-4393-9E6F-B14F50670E31}|线路|4.05|||线路取费表|2088570123.240896|架线工程材料工地运输||5.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1824100000|一般线路本体工程/架线工程/架线工程材料工地运输|项目划分|{A000AD2A-24D9-49BC-B3E0-0303E2CF6988}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{BEFD4073-34E0-4CD1-BAE8-4A6AD42AE6E8}|线路|4.05|||线路取费表|2755648799.032277|导地线架设||5.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1824200000|一般线路本体工程/架线工程/导地线架设|项目划分|{A000AD2A-24D9-49BC-B3E0-0303E2CF6988}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{B1832D94-B27A-4EC2-9EFF-070243607C71}|线路|4.05|||线路取费表|150204.672365|导地线跨越架设||5.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1824300000|一般线路本体工程/架线工程/导地线跨越架设|项目划分|{A000AD2A-24D9-49BC-B3E0-0303E2CF6988}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{37A67A77-D2AD-4AE0-A434-81369416E8BC}|线路|4.05|||线路取费表|30521.132319|其他架线工程||5.4|11.03|9.89|9.89||-0.95|-0.95|||0|Y1824400000|一般线路本体工程/架线工程/其他架线工程|项目划分|{A000AD2A-24D9-49BC-B3E0-0303E2CF6988}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{15CED8B2-B4F5-411D-96C3-08DE6E778E89}|线路|4.05|FJAZ|元/基||987118056.00908|附件安装工程||6|11.03|9.89|9.89||-0.95|-0.95|||0|Y1825000000|一般线路本体工程/附件安装工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{C020DEA9-12CE-44D3-9F26-3D4430CE98DA}|线路|4.05|||线路取费表|984220884.021268|附件安装工程材料工地运输||6.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1825100000|一般线路本体工程/附件安装工程/附件安装工程材料工地运输|项目划分|{15CED8B2-B4F5-411D-96C3-08DE6E778E89}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{5BFDA942-AB13-4868-BB8C-61669ED4FDA0}|线路|4.05||||2897171.987812|绝缘子串及金具安装||6.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1825200000|一般线路本体工程/附件安装工程/绝缘子串及金具安装|项目划分|{15CED8B2-B4F5-411D-96C3-08DE6E778E89}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4FB683E4-6D81-4605-9C36-C82A835186C6}|线路|4.05|||线路取费表|1645706.953768|耐张绝缘子串及金具安装||6.2.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1825201000|一般线路本体工程/附件安装工程/绝缘子串及金具安装/耐张绝缘子串及金具安装|项目划分|{5BFDA942-AB13-4868-BB8C-61669ED4FDA0}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{B19EEA86-4F92-4F81-BD40-AFACDDC2307F}|线路|4.05|||线路取费表|1251465.034044|悬垂绝缘子串及金具安装||6.2.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1825202000|一般线路本体工程/附件安装工程/绝缘子串及金具安装/悬垂绝缘子串及金具安装|项目划分|{5BFDA942-AB13-4868-BB8C-61669ED4FDA0}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|线路|4.05|FZGC|元/km(m³)||1046253.413524|辅助工程||7|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826000000|一般线路本体工程/辅助工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{580B87FF-E6D8-4333-9C8C-E7588ABE29F1}|线路|4.05|||线路取费表|325205.417877|尖峰、施工基面土石方工程||7.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826100000|一般线路本体工程/辅助工程/尖峰、施工基面土石方工程|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4D072EAA-BFAC-4094-A7E3-B33987033455}|线路|4.05||||709931.901393|护坡、挡土墙及排洪沟||7.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826200000|一般线路本体工程/辅助工程/护坡、挡土墙及排洪沟|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{DF775FE5-9C9A-4667-BB5F-3B2E3BD04600}|线路|4.05|||线路取费表|0|护坡、挡土墙及排洪沟材料工地运输||7.2.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826201000|一般线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟材料工地运输|项目划分|{4D072EAA-BFAC-4094-A7E3-B33987033455}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{A5915FEF-6831-44B6-9F24-E984779F4884}|线路|4.05|||线路取费表|0|护坡、挡土墙及排洪沟土石方工程||7.2.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826202000|一般线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟土石方工程|项目划分|{4D072EAA-BFAC-4094-A7E3-B33987033455}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{77FD6CAC-D2BA-4BDB-9E25-2264FEA7E23E}|线路|4.05|||线路取费表|709931.901393|护坡、挡土墙及排洪沟砌筑||7.2.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826203000|一般线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟砌筑|项目划分|{4D072EAA-BFAC-4094-A7E3-B33987033455}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{F4C2EF3B-1242-41DF-9189-AE4F2A037DE8}|线路|4.05||||0|基础永久性围堰||7.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826300000|一般线路本体工程/辅助工程/基础永久性围堰|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{323AB7AE-60E8-44DF-9929-6C45325B02C2}|线路|4.05|||线路取费表|0|基础永久性围堰材料工地运输||7.3.1|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826301000|一般线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰材料工地运输|项目划分|{F4C2EF3B-1242-41DF-9189-AE4F2A037DE8}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{3FEB5513-3399-4CBF-B660-E5D5D8C700DD}|线路|4.05|||线路取费表|0|基础永久性围堰土石方工程||7.3.2|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826302000|一般线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰土石方工程|项目划分|{F4C2EF3B-1242-41DF-9189-AE4F2A037DE8}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{254143D7-57DF-43C2-88FD-2E928CD7404C}|线路|4.05|||线路取费表|0|基础永久性围堰砌筑||7.3.3|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826303000|一般线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰砌筑|项目划分|{F4C2EF3B-1242-41DF-9189-AE4F2A037DE8}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{963579D2-02F0-44FC-9A52-CC4A4398593D}|线路|4.05|||线路取费表|0|索道站安装||7.4|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826400000|一般线路本体工程/辅助工程/索道站安装|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{7D8C3522-1CCD-4D8B-8B56-B9940D9F5351}|线路|4.05|||线路取费表|11116.094254|杆塔上装的各类辅助生产装置||7.5|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826500000|一般线路本体工程/辅助工程/杆塔上装的各类辅助生产装置|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{91C973AE-4C3F-46AF-8CA3-BBECD94CE08C}|线路|4.05|||线路取费表(调试工程)aa|0|输、送电线路试运||7.6|11.03|9.89|9.89||-0.95|-0.95|||0|Y1826600000|一般线路本体工程/辅助工程/输、送电线路试运|项目划分|{035EE3E1-09A8-4C52-AE7C-3DB6F74B3A55}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{7818F2F3-0538-41F3-8119-7DF286BBD89B}|线路|4.05|||线路取费表|114112.536716|电缆工程||8|11.03|9.89|9.89||-0.95|-0.95|||0|Y1827000000|一般线路本体工程/电缆工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{F014C467-967E-4C77-8DE4-C176CA13AC34}|线路|4.05|||线路取费表|114112.536716|通信线路工程||9|11.03|9.89|9.89||-0.95|-0.95|||0|Y1828000000|一般线路本体工程/通信线路工程|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
|{4D8A2C99-1BD5-4A98-BFE1-CF2491B24F39}|线路|4.05|||线路取费表|114112.536716|新增项目名称||10|11.03|9.89|9.89||-0.95|-0.95|01||0||一般线路本体工程/新增项目名称|项目划分|{18C06BBF-4B8B-4390-ABD6-982AFE876DF3}|{29FA8B83-6418-42FF-80E4-150D8A7DFF39}|
@@ -0,0 +1,79 @@
# 其他费用
备注:其他费用表被称为“工程费用中其他费用明细”。其他费用是指为完成工程项目建设所必需的,但不属于建筑工程费、安装工程费、设备购置费、基本预备费的其他相关费用。包括建设场地征用及清理费、项目建设管理费、项目建设技术服务费、生产准备费、大件运输措施费、专业爆破服务费等。查询示例: SELECT Rate FROM OtherFee WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:nodeType
- 字段名称:relTbId
- 字段名称:parentId
- 字段名称:序号
- 备注:序号,序列号
- 字段名称:名称
- 备注:项目名,费用名,名称
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:金额,价格
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:金额
- 备注:金额,价格
- 字段名称:编码
- 备注:WBS编号,WBS编码
- 字段名称:服务内容
- 字段名称:费用归属
- 字段名称:输出
- 字段名称:不可竞争费用
- 字段名称:编制依据
- 备注:编制依据,编制来源
- 字段名称:备注
- 备注:备注,说明
- 字段名称:表一显示
- 字段名称:税率
|_id|nodeType|relTbId|parentId|序号|名称|代码|单位|取费基数|费率|金额|编码|服务内容|费用归属|输出|不可竞争费用|编制依据|备注|表一显示|税率|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|31ypohtxibk0|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}||1|建设场地征用及清理费|A||建设场地征用及清理费|100|0|34100000|||否|否|||是|0|
|31ypohtxibk1|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}||2|项目建设管理费|B|||100|897670.519514|34200000|||否|否|||否|0|
|31ypohtxibk2|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.1|项目法人管理费|B1||本体工程费|1.17|114117.972829|34210000|||否|否|||否|0|
|31ypohu007wg|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.2|招标费|B2||本体工程费|0.28|27310.284096|34220000|||否|否||线路长度超过500km时,超过部分每增加100km,费率乘以0.92系数 |否|6|
|31ypohu007wh|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.3|工程监理费|B3||工程监理费|100|710400|34230000|||否|否|@工程监理费取费基数|说明:162号文指导费率区间:单回路1.22-1.23(万元/km);同杆(塔)双回1.54-1.55(万元/km)。|否|6|
|31ypohu007wi|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.4|设备材料监造费|B4|||100|0|34240000|||否|否|||否|6|
|31ypohu2i48w|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.5|施工过程造价咨询及竣工结算审核费|B5||本体工程费|0.47|45842.262589|34260000|||否|否||1:如只开展工程竣工结算审核工作,按本费率乘以 0.75 系数。2:架空交流输电线路长度超过 300km 时,超过部分乘以 0.8 系数;架空直 流输电线路长度超过 1500km 时,超过部分乘以 0.8 系数。3:费用计算低于 3000 元时,按 3000 元计列。|否|6|
|31ypohu2i48x|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohtxibk1|2.6|工程保险费|B6|||100|0|34250000|||否|否|||否|6|
|31ypohu2i48y|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}||3|项目建设技术服务费|C|||100|316502.117709|34300000|||否|否|||否|6|
|31ypohu2i48z|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.1|项目前期工作费|C1|||100|0|34310000|||否|否|||否|6|
|31ypohu500lc|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.1|可行性研究费用|C11|||100|0||||否|否||说明:162号文指导费用区间:20万元-30万元;20km以上,增加1万元/km;多回路、高海拔等可调整。|否|6|
|31ypohu500ld|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.2|环境影响评价费用|C12|||100|0||||否|否||说明:162号文指导费用区间:5万元-10万元;20km以上,增加0.25万元/km;穿越环境敏感区、平行走廊等可调整。|否|6|
|31ypohu7hwxs|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.3|建设项目规划选址费|C13|||100|0||||否|否||说明:162号文指导费用区间:5万元-10万元;20km以上,增加0.15万元/km;平行走廊等可调整。|否|6|
|31ypohu7hwxt|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.4|水土保持方案编审费用|C14|||100|0||||否|否||说明:162号文指导费用区间:4万元-9万元;20km以上,增加0.2万元/km;平行走廊等可调整。|否|6|
|31ypohu7hwxu|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.5|地质灾害危险性评估费用|C15|||100|0||||否|否||说明:162号文指导费用区间:3万元-5万元;20km以上,增加0.15万元/km;平行走廊等可调整。|否|6|
|31ypohu9zta8|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.6|地震安全性评价费用|C16|||100|0||||否|否||说明:线路工程原则上不计此费用|否|6|
|31ypohu9zta9|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.7|文物调查费用|C17|||100|0||||否|否||说明:162号文指导费用区间:3万元-10万元;20km以上,增加0.05-0.15万元/km;平行走廊等可调整。|否|6|
|31ypohu9ztaa|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.8|矿产压覆评估费用|C18|||100|0||||否|否||说明:162号文指导费用区间:5万元-8万元;20km以上,增加0.1-0.4万元/km;平行走廊等可调整。|否|6|
|31ypohu9ztab|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.9|用地预审费用|C19|||100|0||||否|否||说明:162号文指导费用区间:5万元-15万元;20km以上,增加0.1-0.3万元/km;平行走廊等可调整。|否|6|
|31ypohuchpmo|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.10|节能评估费用|C1A|||100|0||||否|否||说明:162号文指导费用区间:3万元-6万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31ypohuchpmp|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.11|社会稳定风险评估费用|C1B|||100|0||||否|否||说明:162号文指导费用区间:8万元-10万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31ypohuezlz4|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.12|使用林地可行性研究费用|C1C|||100|0||||否|否||说明:162号文指导费用区间:5万元-10万元;20km以上,增加0.1万元/km。|否|6|
|31ypohuezlz5|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48z|3.1.13|前期工作管理费用|C1D|||100|0||||否|否||说明:162号文指导费用:20万元;单独的变电站、换流站、输电线路工程按40%-60%调整|否|6|
|31ypohuezlz6|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.2|知识产权转让与研究试验费|C2|||100|0|34320000|||否|否||根据建设项目法人提出的项目和费用计列|否|6|
|31ypohuezlz7|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.3|勘察设计费|C3|||100|0|34330000|||否|否|||否|6|
|31ypohuezlz8|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohuezlz7|3.3.1|勘察费|C31||勘察费|100|0||||否|否|||否|6|
|31ypohuhhibk|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohuezlz7|3.3.2|设计费|C32||设计费|100|0||||否|否|||否|6|
|31ypohuhhibl|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.4|设计文件评审费|C4|||100|236522|34340000|||否|否|||否|6|
|31ypohuhhibm|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohuhhibl|3.4.1|可行性研究文件评审费|C41||可行性研究评审费|100|56914|34341000|||否|否|@可行性研究评审费取费基数||否|6|
|31ypohujzeo0|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohuhhibl|3.4.2|初步设计文件评审费|C42||初步设计评审费|100|80652|34342000|||否|否|@初步设计评审费取费基数||否|6|
|31ypohujzeo1|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohuhhibl|3.4.3|施工图文件评审费|C43||施工图评审费|100|98956|34343000|||否|否|@施工图评审费取费基数||否|6|
|31ypohumhb0g|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.5|项目后评价费|C5||本体工程费|0.5|48768.364457|34350000|||否|否||线路长度超过500km时,超过部分每增加200km,费率乘以0.92系数|否|6|
|31ypohumhb0h|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.6|工程建设检测费|C6|||100|21458.080361|34360000|||否|否|||否|6|
|31ypohumhb0i|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohumhb0h|3.6.1|电力工程质量检测费|C61||本体工程费|0.22|21458.080361|34361000|||否|否|||否|6|
|31ypohumhb0j|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohumhb0h|3.6.2|特种设备安全监测费|C62|||100|0|34362000|||否|否|||否|6|
|31ypohuoz7cw|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohumhb0h|3.6.3|环境监测及环境保护验收费|C63|||100|0|34363000|||否|否|||否|6|
|31ypohuoz7cx|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohumhb0h|3.6.4|水土保持监测及验收费|C64|||100|0|34364000|||否|否|||否|6|
|31ypohuoz7cy|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohumhb0h|3.6.5|桩基检测费|C65|||100|0|34365000|||否|否|||否|6|
|31ypohuoz7cz|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohu2i48y|3.7|电力工程技术经济标准编制费|C7||本体工程费|0.1|9753.672891|34370000|||否|否|||否|6|
|31ypohurh3pc|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}||4|生产准备费|D|||100|54620.568192|34500000|||否|否|||否|0|
|31ypohurh3pd|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohurh3pc|4.1|管理车辆购置费|D1||本体工程费|0.25|24384.182228|34510000|||否|否||注:如果管理车辆由项目法人单位统一配置,并且不在工程项目中分摊相关费用时,本项费用不计。|否|13|
|31ypohurh3pe|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohurh3pc|4.2|工器具及办公家具购置费|D2||本体工程费|0.21|20482.713072|34520000|||否|否|||否|13|
|31ypohutz01s|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}|31ypohurh3pc|4.3|生产职工培训及提前进场费|D3||本体工程费|0.1|9753.672891|34530000|||否|否|||否|0|
|31ypohuwgwe8|其他费用|{08D3C3D2-A5F1-4BFB-8ABA-20DE6A4FF7E2}||5|专业爆破服务费|E|||100|0||||否|否|||否|0|
@@ -0,0 +1,33 @@
# 大型土石方取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{66580D06-D301-47AB-B9B3-EA8E00A0EE81}|FFZ1|||一|否|100|直接工程费|取费表||{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{A2994CFA-9C39-4CC0-931F-CDF3B975096C}|RGF|取费定额人工费||1|否|100|人工费|取费表|{66580D06-D301-47AB-B9B3-EA8E00A0EE81}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{189238D9-CCEF-4CBE-9C07-8A163D8F1A60}|CLF|取费定额乙供材料费不含税+乙供取费主材费不含税+甲供取费主材费含税||2|否|100|材料费|取费表|{66580D06-D301-47AB-B9B3-EA8E00A0EE81}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{12925CE8-5EBF-40A7-830B-BBC269C110BD}|JXF|取费定额机械费||3|否|100|施工机械使用费|取费表|{66580D06-D301-47AB-B9B3-EA8E00A0EE81}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{2B8E4089-C32F-4F71-B717-3CB4BF36965D}|TZHQF|FFZ1-甲供主材进项税额|综合取费费用额(包含措施费、间接费、利润)|二|否|17.79|综合取费费用额|取费表||{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{4BB0249B-EAE2-42AD-81E4-B44953711237}|JC|||三|否|100|编制基准期价差|取费表||{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{C4DEF5ED-4C41-4459-A06D-2408A5E7307E}|RJC|人工价差||1|否|100|人工价差|取费表|{4BB0249B-EAE2-42AD-81E4-B44953711237}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{6A6A3327-D33F-4D75-A194-8290B2CDAA97}|CJC|乙供材料价差不含税+乙供主材价差不含税+甲供主材价差含税||2|否|100|材料价差|取费表|{4BB0249B-EAE2-42AD-81E4-B44953711237}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{08216E49-E3DA-474F-9A44-1C4997314436}|JJC|机械价差||3|否|100|机械价差|取费表|{4BB0249B-EAE2-42AD-81E4-B44953711237}|{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{21290DD4-8C6C-4920-A18B-BAE24913FFB4}|TFFS|FFZ1+TZHQF+JC-甲供取费主材费含税-甲供主材价差含税+不取费定额费不含税+不取费乙供主材费不含税||四|否|9|税金|取费表||{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
|{FBA7D80D-BAD6-49C6-8331-1DBF238B286D}|THJ|FFZ1+TZHQF+TFFS+JC+一笔性费用+不取费定额费不含税+不取费乙供主材费不含税+不取费甲供主材费含税||五|否|100|合计|取费表||{0EB26EB9-93C0-4DC4-9BE7-1A294CC09231}|
@@ -0,0 +1,61 @@
# 线路取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{C2BB0788-B663-48D4-ABE4-010F21D6808C}|FFZ|||一|否|100|直接费|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{3220321B-AD5E-45AA-9103-EF047C3DF792}|FFZ1|||1|否|100|直接工程费|取费表|{C2BB0788-B663-48D4-ABE4-010F21D6808C}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{7158E9FA-5C36-42B4-9C39-A974556EDADB}|DZF|||1.1|否|100|定额直接费|取费表|{3220321B-AD5E-45AA-9103-EF047C3DF792}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{43B740B1-5953-4E0E-A2B4-840DF8C96B65}|RGF|取费定额人工费||1.1.1|否|100|人工费|取费表|{7158E9FA-5C36-42B4-9C39-A974556EDADB}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{9CC2293B-D8F5-471F-9EBC-F906C0E60546}|CLF|取费定额乙供材料费不含税||1.1.2|否|100|材料费|取费表|{7158E9FA-5C36-42B4-9C39-A974556EDADB}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{9DABE30D-3E2C-4C2B-BDB3-18668E7B4184}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{7158E9FA-5C36-42B4-9C39-A974556EDADB}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{0A7CB88C-67A9-4578-878B-3CEACEFFD63E}|ZZCF|||1.2|否|100|装置性材料费|取费表|{3220321B-AD5E-45AA-9103-EF047C3DF792}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{AB28917C-D9F7-4A3C-94A6-99DA9ABB5D51}|JZZCF|甲供取费主材费含税||1.2.1|否|100|甲供装置性材料费|取费表|{0A7CB88C-67A9-4578-878B-3CEACEFFD63E}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{C5FE17B3-E6AC-4326-ACA8-7B5BA750AC05}|YZZCF|乙供取费主材费不含税||1.2.2|否|100|乙供装置性材料费|取费表|{0A7CB88C-67A9-4578-878B-3CEACEFFD63E}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{1F5E655F-A6E4-4853-8838-A79344A80B60}|FFZ2|||2|否|100|措施费|取费表|{C2BB0788-B663-48D4-ABE4-010F21D6808C}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{3E8DA03C-75F9-4054-A638-FBFEBEB38D79}|DYF|取费定额人工费||2.1|否|4.59|冬雨季施工增加费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{D80D263C-8251-4075-9BB5-ECDB41C77CAB}|YSF|取费定额人工费||2.2|否|0|夜间施工增加费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{E597BC41-1597-4891-8230-F939704B51E4}|SYF|取费定额人工费||2.3|否|3.82|施工工具用具使用费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{12A0EE6D-1BDF-4A9B-8F9B-A76A5658B142}|TDF|取费定额人工费||2.4|否|4.73|特殊地区施工增加费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{992D8A46-E25D-44E3-87AD-EE283D4D0E76}|LSF|DZF||2.5|否|6.6|临时设施费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{C147B8E9-7CF2-489E-B196-D1F4A5BD9EEA}|ZYF|取费定额人工费||2.6|否|2.24|施工机构迁移费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{24ED26D7-D9C3-44FC-AAA4-7221EF2C078C}|BZF|FFZ1-甲供主材进项税额||2.7|否|3.55|安全文明施工费|取费表|{1F5E655F-A6E4-4853-8838-A79344A80B60}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{9C52DEA5-8FE5-4D50-BF25-2E4E3B513774}|FFJ|||二|否|100|间接费|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{CC8ED3BC-3A7E-4A7C-8BB5-E478DE0F04C4}|GF|||1|否|100|规费|取费表|{9C52DEA5-8FE5-4D50-BF25-2E4E3B513774}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{EFCF4B8E-DCF7-4F3E-BF69-2CECDE4FABFD}|BZHF|取费定额人工费*1.05||1.1|否|0|社会保险费|取费表|{CC8ED3BC-3A7E-4A7C-8BB5-E478DE0F04C4}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{70DE8958-8BDE-440C-B0E4-D612E4642A53}|GJJ|取费定额人工费*1.05||1.2|否|0|住房公积金|取费表|{CC8ED3BC-3A7E-4A7C-8BB5-E478DE0F04C4}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{BB2E72B2-F3ED-47DF-853E-182E11450C18}|GLF|取费定额人工费||2|否|35.76|企业管理费|取费表|{9C52DEA5-8FE5-4D50-BF25-2E4E3B513774}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{20768999-355E-4C7D-A97E-FBEF73BE11D0}|TSF|DZF||3|否|1.06|施工企业配合调试费|取费表|{9C52DEA5-8FE5-4D50-BF25-2E4E3B513774}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{72681D8D-FD6C-446A-BF6E-91C87E7F1081}|FFR|FFZ+FFJ-甲供主材进项税额||三|否|5|利润|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{5E523944-7B59-41E7-923D-8DBFEDBBA075}|JC|||四|否|100|编制基准期价差|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{E49FD193-1FD7-49A8-B539-0DF5A775F08E}|RJC|人工价差||1|否|100|人工价差|取费表|{5E523944-7B59-41E7-923D-8DBFEDBBA075}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{1CD04D11-91CA-494D-9E6B-015E1045AA9A}|CJC|乙供材料价差不含税||2|否|100|材料价差|取费表|{5E523944-7B59-41E7-923D-8DBFEDBBA075}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{9038C70C-128F-44E5-A572-E605555B620C}|JJC|机械价差||3|否|100|机械价差|取费表|{5E523944-7B59-41E7-923D-8DBFEDBBA075}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{5553B7F5-7675-4A56-84E6-D6A4319A83E6}|ZCJC|||4|否|100|装置性材料价差|取费表|{5E523944-7B59-41E7-923D-8DBFEDBBA075}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{BB9FC5EF-C745-4EFC-AEF2-285E72FDB92B}|JZCJC|甲供主材价差含税||4.1|否|100|甲供装置性材料价差|取费表|{5553B7F5-7675-4A56-84E6-D6A4319A83E6}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{B18A36DE-378E-4BCF-92BE-906A2FB8E9A2}|YZCJC|乙供主材价差不含税||4.2|否|100|乙供装置性材料价差|取费表|{5553B7F5-7675-4A56-84E6-D6A4319A83E6}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{A7906649-518C-428D-B6D2-6A512787923C}|FFS|FFZ+FFJ+FFR+JC-甲供取费主材费含税-甲供主材价差含税+不取费定额费不含税+不取费乙供主材费不含税||五|否|9|税金|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{C56D6329-53EB-4406-9C80-FD824209A11F}|SBF|||六|否|100|设备费|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{250A2E7B-314E-47AF-974D-F046AA556D40}|SBY|乙供设备费不含税+乙供设备税金||1|否|100|乙供设备不含税价|取费表|{C56D6329-53EB-4406-9C80-FD824209A11F}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{A294E14E-41D0-4478-91C6-6F62713E5B23}|SBJ|甲供设备费含税||2|否|100|甲供设备含税价|取费表|{C56D6329-53EB-4406-9C80-FD824209A11F}|{77980093-5E58-4007-A090-23749D60D5B0}|
|{2ADA195C-CD85-4263-8049-21A714B30D25}|AZF|DZF+FFZ2+FFJ+FFR+FFS+JC-ZCJC+不取费定额费不含税+一笔性费用||七|否|100|安装费|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{AAE32372-BB8A-42F8-B14A-BAB8B99E74F1}|ZCF|ZZCF+ZCJC+不取费乙供主材费不含税+不取费甲供主材费含税||八|否|100|主材费|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{8F219987-A153-424A-A957-35AB2C6D1DD2}|ZJ|AZF+ZCF+SBF||九|否|100|总计|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
|{BAF0142D-07CC-49EF-BAC6-17BBEB974434}|HJ|ZJ-SBF||十|否|100|合计|取费表||{77980093-5E58-4007-A090-23749D60D5B0}|
@@ -0,0 +1,31 @@
# 线路取费表(余物清理)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{E034EFE6-A929-49A9-BF28-900C05CE528E}|FFZ|||一|否|100|直接费|取费表||{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{2E18CA1D-BD04-43AF-8870-D8917C3D31F9}|FFZ1|||1|否|100|直接工程费|取费表|{E034EFE6-A929-49A9-BF28-900C05CE528E}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{BA1176CE-0768-4225-8370-86E1EFE29BEB}|DZF|||1.1|否|100|定额直接费|取费表|{2E18CA1D-BD04-43AF-8870-D8917C3D31F9}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{381A9E4F-07F6-4CD8-A860-50C08B9004E3}|RGF|取费定额人工费||1.1.1|否|100|人工费|取费表|{BA1176CE-0768-4225-8370-86E1EFE29BEB}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{B9DE90CA-1159-4120-9815-E761297C3DBE}|CLF|取费定额乙供材料费不含税||1.1.2|否|100|材料费|取费表|{BA1176CE-0768-4225-8370-86E1EFE29BEB}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{F02F21B5-1A13-48CC-AEEB-C9AC2732F410}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{BA1176CE-0768-4225-8370-86E1EFE29BEB}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{E856825F-C2FD-44C8-A104-4A1995F171EC}|FFZ2|||2|否|100|措施费|取费表|{E034EFE6-A929-49A9-BF28-900C05CE528E}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{40652335-FB10-4FBC-B20E-64E997CEC268}|BZF|FFZ1||2.1|否|3.55|安全文明施工费|取费表|{E856825F-C2FD-44C8-A104-4A1995F171EC}|{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
|{CC2FD840-E9DA-4E18-BBD5-0097FDB3A640}|HJ|FFZ+一笔性费用||二|否|100|合计|取费表||{6B30DC7A-105A-45BD-92F1-ED8455E5D3E0}|
@@ -0,0 +1,46 @@
# 线路取费表(拆除)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{8C5BCA4E-0CCF-48A7-AC6F-42B62A1C5167}|FFZ|||一|否|100|直接费|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{E744579B-7124-49C6-9FAC-37CC22F01E36}|FFZ1|||1|否|100|直接工程费|取费表|{8C5BCA4E-0CCF-48A7-AC6F-42B62A1C5167}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{20392A4B-F64C-4400-937E-F9D4B4FC3922}|RGF|取费定额人工费||1.1|否|100|人工费|取费表|{E744579B-7124-49C6-9FAC-37CC22F01E36}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{42385797-BF6F-4CA1-A4EE-2F787D427BEB}|CLF|取费定额乙供材料费不含税||1.2|否|100|材料费|取费表|{E744579B-7124-49C6-9FAC-37CC22F01E36}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{5840FCA7-34B9-44FA-8BF3-A7C4AF3CA0B0}|JXF|取费定额机械费||1.3|否|100|施工机械使用费|取费表|{E744579B-7124-49C6-9FAC-37CC22F01E36}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{3D68CDB3-BB8F-4767-B049-056391AC377A}|FFZ2|||2|否|100|措施费|取费表|{8C5BCA4E-0CCF-48A7-AC6F-42B62A1C5167}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{77AB31B4-9641-4CC8-86F3-4A792DC95EDC}|DYF|取费定额人工费+取费定额机械费||2.1|否|2.16|冬雨季施工增加费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{7232E573-CD0B-4B33-A0F2-83B02C58D785}|SYF|取费定额人工费+取费定额机械费||2.2|否|0.65|施工工具用具使用费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{2F1BA992-F037-40E4-8B4E-E818523E9796}|TDF|取费定额人工费+取费定额机械费||2.3|否|3.1|特殊地区施工增加费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{1DA5F8FE-6256-4227-9513-2AE56D8BCBFD}|LSF|取费定额人工费+取费定额机械费|独立的拆除工程可计取此项费,与其他工程同期实施的拆除工作不计取此项费用|2.4|否|0|临时设施费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{82E0248B-A916-4262-91DD-8CE22AA8FB78}|ZYF|取费定额人工费+取费定额机械费|独立的拆除工程可计取此项费,与其他工程同期实施的拆除工作不计取此项费用|2.5|否|0|施工机构迁移费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{4CFE2267-B895-457F-AE71-7732E31FE39C}|BZF|取费定额人工费+取费定额机械费||2.6|否|11.31|安全文明施工费|取费表|{3D68CDB3-BB8F-4767-B049-056391AC377A}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{B3790072-A433-4934-B99E-1ED92F669FEC}|FFJ|||二|否|100|间接费|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{3C9E8743-3DDB-49DE-B7EC-BF591B041CDF}|GF|||1|否|100|规费|取费表|{B3790072-A433-4934-B99E-1ED92F669FEC}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{FA22E0F0-95D2-4E0B-BC1F-66768819952F}|BZHF|取费定额人工费*1.05||1.1|否|0|社会保险费|取费表|{3C9E8743-3DDB-49DE-B7EC-BF591B041CDF}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{20ED2D03-F04F-43DA-95B2-5F60BDBE8EF5}|GJJ|取费定额人工费*1.05||1.2|否|0|住房公积金|取费表|{3C9E8743-3DDB-49DE-B7EC-BF591B041CDF}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{64528BE4-F8DA-4309-B137-957757A4D396}|GLF|取费定额人工费+取费定额机械费||2|否|17.13|企业管理费|取费表|{B3790072-A433-4934-B99E-1ED92F669FEC}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{430AA4DD-76C3-427C-8465-5A545ABD04A0}|FFR|取费定额人工费+取费定额机械费||三|否|5.24|利润|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{399635B6-E3AD-46A2-BD75-D32C7C893418}|JC|||四|否|100|编制基准期价差|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{4F2DE62A-27A6-4C4D-B63A-A45CF6D31815}|RJC|人工价差||1|否|100|人工价差|取费表|{399635B6-E3AD-46A2-BD75-D32C7C893418}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{1CF69151-BC79-476A-95D1-282137C9436D}|CJC|乙供材料价差不含税||2|否|100|材料价差|取费表|{399635B6-E3AD-46A2-BD75-D32C7C893418}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{B2426FFA-B1FF-470F-823A-2CF9A93E2221}|JJC|机械价差||3|否|100|机械价差|取费表|{399635B6-E3AD-46A2-BD75-D32C7C893418}|{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{B5E15771-82CD-467A-B3E8-EA8EFFBCC6C6}|FFS|FFZ+FFJ+FFR+JC+不取费定额费不含税||五|否|9|税金|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
|{6852EB92-6930-4CA0-89DB-EB756398B1FF}|HJ|FFZ+FFJ+FFR+FFS+JC+一笔性费用+不取费定额费不含税||六|否|100|合计|取费表||{01247A42-E488-4FD7-89FE-4756DA791CC7}|
@@ -0,0 +1,54 @@
# 线路取费表(调试工程)_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{15ABD61A-042B-4BB5-A40B-8CE980A39CAC}|FFZ|||一|否|100|直接费|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{93BF1F57-992F-4313-94EC-BCC16E77DCEC}|FFZ1|||1|否|100|直接工程费|取费表|{15ABD61A-042B-4BB5-A40B-8CE980A39CAC}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{3E1F2E4C-5220-462F-8A54-44582CE1B055}|DZF|||1.1|否|100|定额直接费|取费表|{93BF1F57-992F-4313-94EC-BCC16E77DCEC}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{6105958B-8721-498C-A4D5-58720116530C}|RGF|取费定额人工费||1.1.1|否|100|人工费|取费表|{3E1F2E4C-5220-462F-8A54-44582CE1B055}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{13F2B44B-DB9F-4A8E-A5CB-1E68CFB3A072}|CLF|取费定额乙供材料费不含税||1.1.2|否|100|材料费|取费表|{3E1F2E4C-5220-462F-8A54-44582CE1B055}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{77D48426-5E27-4556-8C64-544841E0CFAE}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{3E1F2E4C-5220-462F-8A54-44582CE1B055}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{7ECB7FF4-7101-431D-8EFF-B96627F2942D}|ZZCF|||1.2|否|100|装置性材料费|取费表|{93BF1F57-992F-4313-94EC-BCC16E77DCEC}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{C5D25B31-3086-4870-B28D-7B824AD10DE6}|JZZCF|甲供取费主材费含税||1.2.1|否|100|甲供装置性材料费|取费表|{7ECB7FF4-7101-431D-8EFF-B96627F2942D}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{6D8E21BF-2A69-4B37-8E5E-C3235351FF79}|YZZCF|乙供取费主材费不含税||1.2.2|否|100|乙供装置性材料费|取费表|{7ECB7FF4-7101-431D-8EFF-B96627F2942D}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|FFZ2|||2|否|100|措施费|取费表|{15ABD61A-042B-4BB5-A40B-8CE980A39CAC}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{9CA6ED0D-557F-4D41-A454-C4B2A20A1796}|DYF|取费定额人工费||2.1|否|9|冬雨季施工增加费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{6169CAD0-3C75-486D-B749-B9F8E8F730CC}|YSF|取费定额人工费||2.2|否|0|夜间施工增加费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{F526AB28-3AE3-440A-9060-C59F60312609}|SYF|取费定额人工费||2.3|否|3.82|施工工具用具使用费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{2A37FE41-DF35-4630-B07B-F984A362BE97}|TDF|取费定额人工费||2.4|否|4.73|特殊地区施工增加费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{DE5C5568-7231-4DF4-8E7F-E0996291EE80}|LSF|DZF||2.5|否|6.6|临时设施费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{C85AFC7D-8222-4F0A-B01B-E5AF8A76F0D2}|ZYF|取费定额人工费||2.6|否|2.24|施工机构迁移费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{F996F96C-962C-4E2A-949B-4B4ECAEFCE37}|BZF|FFZ1-甲供主材进项税额||2.7|否|3.55|安全文明施工费|取费表|{D9897015-5B7E-48CC-BE9E-C92630A741A3}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{458D3730-C862-47C2-8E79-E40CC2F8CF0C}|FFJ|||二|否|100|间接费|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{FD336C8D-C86E-4C65-B45D-BC675AF4ABA2}|GF|||1|否|100|规费|取费表|{458D3730-C862-47C2-8E79-E40CC2F8CF0C}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{908F0983-9649-4570-BB81-0B4A53DF6C50}|BZHF|取费定额人工费*1.05||1.1|否|0|社会保险费|取费表|{FD336C8D-C86E-4C65-B45D-BC675AF4ABA2}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{3D8BE9DA-DD9E-4CB2-9B28-3346115F9185}|GJJ|取费定额人工费*1.05||1.2|否|0|住房公积金|取费表|{FD336C8D-C86E-4C65-B45D-BC675AF4ABA2}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{D63FCFEB-DD3D-4990-A7F1-FAC0F8A6F7BC}|GLF|取费定额人工费||2|否|35.76|企业管理费|取费表|{458D3730-C862-47C2-8E79-E40CC2F8CF0C}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{E74E7565-809E-42CC-886C-5351E5B4D68C}|FFR|FFZ+FFJ-甲供主材进项税额||三|否|5|利润|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{2A6A4CF6-F523-4043-987D-A5CB34E16EF9}|JC|||四|否|100|编制基准期价差|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{994FA147-C34F-4857-9109-0F0319B73A18}|RJC|人工价差||1|否|100|人工价差|取费表|{2A6A4CF6-F523-4043-987D-A5CB34E16EF9}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{C457CDD7-26E0-4D1B-80BF-4880E8660958}|CJC|乙供材料价差不含税||2|否|100|材料价差|取费表|{2A6A4CF6-F523-4043-987D-A5CB34E16EF9}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{C4700525-5629-4ABE-A4ED-30E1EF37C5B9}|JJC|机械价差||3|否|100|机械价差|取费表|{2A6A4CF6-F523-4043-987D-A5CB34E16EF9}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{100A69D7-12A5-419C-AF6D-B4F952B82257}|ZCJC|||4|否|100|装置性材料价差|取费表|{2A6A4CF6-F523-4043-987D-A5CB34E16EF9}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{F6C2A23D-FDE1-4AFA-8AAF-ACD3056299F5}|JZCJC|甲供主材价差含税||4.1|否|100|甲供装置性材料价差|取费表|{100A69D7-12A5-419C-AF6D-B4F952B82257}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{2EE5A86D-9D41-4C7F-B7E0-656194442E09}|YZCJC|乙供主材价差不含税||4.2|否|100|乙供装置性材料价差|取费表|{100A69D7-12A5-419C-AF6D-B4F952B82257}|{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{B11562C7-0F81-4306-B731-DF2630602BAE}|FFS|FFZ+FFJ+FFR+JC-甲供取费主材费含税-甲供主材价差含税+不取费定额费不含税+不取费乙供主材费不含税||五|否|9|税金|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
|{4BDC880D-B658-4874-9F61-9E7B4466BE46}|HJ|FFZ+FFJ+FFR+FFS+JC+一笔性费用+不取费定额费不含税+不取费乙供主材费不含税+不取费甲供主材费含税||六|否|100|合计|取费表||{0DB69100-1398-4258-87A7-6AD28B8A0659}|
@@ -0,0 +1,213 @@
# 工程属性
备注:工程属性表是用于存储整个工程的重要属性,访问该表都是为了通过属性名查找属性值。通常属性值有工程信息、工程属性、技经参数,表中包含工程总投资、工程总费用,工程主要费用,工程技经参数等。查询示例: SELECT Value FROM ProjectProperties WHERE Name = 'findname'。
- 字段名称:名称
- 字段名称:值
- 备注:属性值,值、变量值、参数值、数值
|名称|值|
|---|---|
|设置线材工地运输计算方式|按实际用量计算|
|材料调差系数|6.2|
|拆除安装材料按系数调差|1|
|甲供材料损耗是否计入甲供材料费|-1|
|计税方式|增值税|
|地形调整及跳跃施工计算顺序|0|
|是否自动计算凿桩头总量|是|
|脚手架材料费系数|0.5|
|云端同步|True|
|线路清单组件库|线路组件库(2018版).zjzjk|
|固定综合单价模式||
|总价万元|1119|
|建筑工程按系数调差|0|
|QtyID|328|
|发布版工程量清单||
|材机是否按系数调差|1|
|材机界面是否只显示新增资源|FALSE|
|计价方式|定额计价|
|升级历史|2.4.0.124;2.4.1.4;2.4.3.3;2.4.4.5;2.5.0.155;2.5.1.14;2.6.0.218;2.6.2.0;2.6.3.0;2.7.0.0;2.8.0.0;3.0.0.0;3.0.1.0;3.1.0.0;3.1.1.0;3.1.2.0;|
|配置选项|2018年版预规|
|工程税率|9|
|取费表显示级别|项目划分级别显示|
|投标人||
|是否第一次打开工程||
|安装人工按系数调差|1|
|是否按单位控制工程量精度|否|
|安装材料按系数调差|1|
|工程阶段||
|脚手架费率|5|
|市场价唯一|是|
|耐张、转角塔导线挂线是否计算综合地形增加费|0|
|地方规范||
|默认自定义拆除定额库|自定义拆除定额库|
|项目类型|架空输电线路工程|
|工程文件预览信息|●工程名称:线路工程20221122●项目划分:架空输电线路工程●工程阶段:初步设计概算●地区类型:Ⅱ类●工程所在地:山东●执行规范:电网预规2018年版●工程版本:3.1.2.4●升级历史:2.4.0.124;2.4.1.4;2.4.3.3;2.4.4.5;2.5.0.155;2.5.1.14;2.6.0.218;2.6.2.0;2.6.3.0;2.7.0.0;2.8.0.0;3.0.0.0;3.0.1.0;3.1.0.0;3.1.1.0;3.1.2.0;●加密属性:|
|甲供材料计入综合单价|是|
|工程所在地|山东|
|岩石灌浆基础超灌量|8|
|阶段类型|概预算|
|施工费记取甲供设备运杂费||
|余土外运量|0|
|脚手架人工费系数|0.4|
|是否开放组件统计|是|
|工程总投资|1118.7803|
|清单规范|2014版|
|灌注桩超灌量|17|
|线路定额统计规则库|线路定额统计规则(2018版).bwgzk6|
|物料增值税率|13|
|工程创建模板|标准配置|
|国网14升21||
|编制单位||
|定额价目本|2006|
|加密属性||
|默认清单组价方式||
|甲供材料是否计取税金||
|导入发布版工程量清单||
|机械调差系数|6.2|
|拆除安装工程默认定额库|拆除预算 第三册 架空线路工程|
|建筑项目划分代码前缀|BT|
|脚手架计算基数|人工费|
|配合比拆分||
|报表类型||
|泥沼地形比例|0|
|平地地形比例|0|
|BCL版本|3.1.2|
|材料单公里用量计算规则|按线路亘长计算|
|工程按系数调差|0|
|专业扩展类型||
|工程编号||
|工程改造性质|新建|
|是否组合件库||
|基本预备费费率|1.5|
|工程默认人材机库||
|是否设置岩石坑排水||
|发布版本|0|
|专业类型|送电|
|相同清单合并|是(清单属性及工程量一致)|
|拆除材料调差系数|5.75|
|标准清单编码长度|3|
|特殊地区|酷热地区|
|塔材代用部分是否计入主材费||
|拆除安装人工按系数调差|1|
|规划台数||
|安装工程默认定额库|预算 第四册 架空输电线路工程(2018年版)|
|默认自定义主材库|自定义材料库|
|安装工程量是否首次统计工程量|否|
|预算转清单||
|工程有效性数据|S08JAAAXw7BVvRAyBEAUBnEVya8p1WMxHUl6cQNgyLBUqGZGBQUVAwdkw7IooGowBg==|
|物料价格联动|是|
|生育保险费缴费费率||
|拆除建筑人工按系数调差|1|
|安装机械按系数调差|1|
|拆除建筑材料按系数调差|0|
|启用自定义安全文明施工费||
|建筑工程默认定额库||
|组件参数汇总错误||
|打开工程是否需要刷新招标人信息||
|浙江接口项目版本|送审版|
|默认自定义设备库|自定义设备库|
|工程调差文件|调差系数文件〔2022年1号文〕|
|监理费计算依据|预规(2018版)|
|工程构成类型||
|山地地形比例|0|
|塔基占地面积|0|
|高山地形比例|0|
|工资津贴补差|0.89|
|安装工程默认清单库|送电线路清单库(2014)|
|工程默认主材库|装置性材料预算价2018|
|录入工程量标记招||
|工程名称|线路工程20221122|
|组价方式|综合单价|
|工程深度||
|失业保险费缴费费率||
|浙江接口项目类型|国网版|
|工程造价咨询法定代表人或其授权人||
|措施规费按清单级取费|1|
|是否为特高压工程||
|编制人||
|安装工程默认规则库|线路典型清单库|
|组合件模式|否|
|工程默认设备库||
|建筑工程默认清单库||
|商品砼预算价||
|塔材以大代小|3|
|建筑人工按系数调差|1|
|表头设置|概算|
|区域类型|国网清单工程|
|工程模式||
|项目划分面板数据加载||
|所区占地面积||
|钻孔爆扩基础超灌量|7|
|建筑工程默认规则库||
|插件名称||
|默认自定义定额库|自定义定额库|
|架线长度|20|
|工程地址||
|人工调差系数|9.58|
|是否生成数据|0|
|调差系数设置默认地区类型|Ⅱ类 地区|
|地方清单规范||
|拆除机械调差系数|5.75|
|本期单台容量||
|工程默认调试库||
|塔材代用部分是否自动计算安装费|0|
|隐藏中标数据||
|工程建筑面积||
|空表显示状态|显示空表|
|安装项目划分代码前缀|BA|
|工伤保险费缴费费率||
|线路清单统计规则库|线路清单统计规则(2014版清单规范).bwqdk6|
|招标控制价导造价接口||
|本期台数||
|中介机构法定(授权)代表人||
|标段||
|拆除安装机械按系数调差|1|
|SID|5100|
|丘陵地形比例|0|
|架线合并方案预算类型||
|编制时间|2022-11-22|
|工程密码||
|拆除建筑机械按系数调差|0|
|脚手架机械费系数|0.1|
|执行规范|电网预规2018年版|
|预算类型|初步设计概算|
|工程描述||
|建筑消材应用调差范围|FALSE|
|养老保险费缴费费率||
|脚手架人工工日系数|0.4|
|现浇护壁超灌量|17|
|招标人||
|规划单台容量||
|医疗保险费缴费费率||
|拆除工程调差文件|2023年上半年调差系数文件(28号文)|
|住房公积金费率|0|
|不同土质定额归属不同清单|是|
|工程版本|3.1.2.4|
|默认组件库|线路组件库(2014版清单规范)|
|一笔性施工企业配合调试费|0|
|峻岭地形比例|0|
|软件名称|博微电力建设计价通软件|
|电压等级|220kV|
|冷却方式||
|资质证书||
|本期容量||
|掏挖基础超灌量|7|
|地区类型|Ⅱ类|
|负责人工号|P|
|招标法定代表人或其授权人||
|编辑时间||
|工程类型|初步设计概算|
|定额版本||
|架线类型|一般线路|
|社会保险费费率|0|
|工程历史版本列表||
|2.3.4升级工程||
|显示全部数据||
|机械台班拆分||
|拆除人工调差系数|7.69|
|只读||
|线路项目划分代码前缀|BA|
|工程造价咨询人||
|拆分材料人工是否调差|是|
|是否重算费用||
|导入工程量清单||
|拆除工程材机按系数调差|0|
@@ -0,0 +1,62 @@
# 总算表
备注:总算表也被称为“工程总费用”、“工程费用”。其中包含本地工程、辅助设施工程、编制基准期价差、设备购置费、其他费用、基本预备费、特殊费用、工程静态投资、动态费用、价差预备费、建设期贷款利息、工程动态投资、可抵扣增值税额。查询示例: SELECT Amount FROM TotalCalculateTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:nodeType
- 字段名称:relTbId
- 字段名称:parentId
- 字段名称:序号
- 备注:序号
- 字段名称:名称
- 备注:项目名,费用名,名称
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:金额_单位投资,合计投资金额
- 字段名称:取费基数
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:金额
- 备注:金额_设备费,设备价格,设备金额
- 字段名称:编码
- 备注:WBS编号,WBS编码
- 字段名称:服务内容
- 字段名称:费用归属
- 字段名称:输出
- 字段名称:不可竞争费用
- 字段名称:编制依据
- 字段名称:备注
- 字段名称:表一显示
- 字段名称:建筑费
- 字段名称:安装费
- 备注:安装金额,安装价格,金额_安装费
- 字段名称:设备费
- 备注:金额_设备费,设备价格,设备金额
- 字段名称:其他费
- 备注:其他费用金额,其他费用价格,金额_其他费
- 字段名称:合计费
- 备注:金额,价格
- 字段名称:占总计
- 备注:总体金额,总的金额,金额_占总计
- 字段名称:单位投资
- 备注:金额_单位投资,合计投资金额
- 字段名称:建安合计费
- 字段名称:金额增减
|_id|nodeType|relTbId|parentId|序号|名称|代码|单位|取费基数|费率|金额|编码|服务内容|费用归属|输出|不可竞争费用|编制依据|备注|表一显示|建筑费|安装费|设备费|其他费|合计费|占总计|单位投资|建安合计费|金额增减|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|31ypohwaevb4|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||一|架空输电线路本体工程|BTGC|%||100|9753672.891356||||是|否|||否|0|9753672.891356|0|0|9753672.891356|87.181306|487683.644568|0|9753672.891356|
|31ypohwfeo00|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|31ypohwaevb4|(一)|一般线路本体工程|XLBT|%||100|9753672.891356||||是|否|||否|0|9753672.891356|0|0|9753672.891356|87.181306|487683.644568|0|9753672.891356|
|31ypohwfeo01|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||二|辅助设施工程|FZSS|%||100|0|3A000000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohwhwkcg|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|||小计|HJ|%||100|9753672.891356||||是|否|||否|0|9753672.891356|0|0|9753672.891356|87.181306|487683.644568|0|9753672.891356|
|31ypohwkegow|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||三|其中:编制基准期价差|JC|元||100|517894.183384|35000000|||是|否|||否|0|517894.183384|0|0|517894.183384|4.629096|25894.709169|0|517894.183384|
|31ypohwmwd1c|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||四|设备购置费|SBGZF|元||100|0||||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohwpe9ds|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||五|其他费用|QTFY|元||100|1268793.205415|34000000|||是|否|||否|0|0|0|1268793.205415|1268793.205415|11.340861|63439.660271|0|1268793.205415|
|31ypohwrw5q8|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|31ypohwpe9ds||其中:建设场地征用及清理费||%||100|0||||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohwue22o|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||六|基本预备费|JBYBF|%||100|165336.991452|38000000|||是|否|||否|0|0|0|165336.991452|165336.991452|1.477833|8266.849573|0|165336.991452|
|31ypohwwvyf4|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||七|特殊项目|TSXM|%||100|0|36000000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohwzdurk|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|||工程静态投资(一~七项合计)|JTTZ|元||100|11187803.088223||||是|否|||否|0|9753672.891356|0|1434130.196866|11187803.088223|100|559390.154411|0|11187803.088223|
|31ypohx1vr40|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}||八|动态费用|DTFY|元||100|0|37000000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohx4dngg|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|31ypohx1vr40|(一)|价差预备费|JCYBF|元||100|0|37100000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohx6vjsw|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|31ypohx1vr40|(二)|建设期贷款利息|DKLX|元||100|0|37200000|||是|否|||否|0|0|0|0|0|0|0|0|0|
|31ypohx9dg5c|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|||工程动态投资(一~八项合计)|DTTZ|元||100|11187803.088223||||是|否|||否|0|9753672.891356|0|1434130.196866|11187803.088223|0|0|0|11187803.088223|
|31ypohxbvchs|总算表|{40159452-528E-4482-8E9D-D961B50B57EF}|||其中:可抵扣增值税额|ZZS|%||100|872778.061193||||是|否|||否|0|805349.137818|0|67428.923375|872778.061193|0|0|0|872778.061193|
@@ -0,0 +1,64 @@
# 项目划分_余物清理
备注:项目划分表是用于存储工程项目划分树状数据。内部包含安装工程项目划分,建筑工程项目划分,线路项目划分,工程分部分项。查询示例: SELECT Sum_Price FROM ProjectDivision WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:专业类型
- 备注:专业类型
- 字段名称:人工调差系数
- 备注:拆除人工调差系数
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:单位
- 字段名称:取费表
- 备注:取费表
- 字段名称:合价
- 备注:合价,合计
- 字段名称:名称
- 备注:项目名,名称
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:项目序号,序号,序列号
- 字段名称:拆除人工调差系数
- 备注:拆除人工调差系数
- 字段名称:拆除机械调差系数
- 备注:拆除机械调差系数
- 字段名称:拆除材料调差系数
- 备注:拆除材料调差系数
- 字段名称:数量
- 备注:数目,数量,个数
- 字段名称:机械调差系数
- 备注:拆除机械调差系数
- 字段名称:材料调差系数
- 备注:拆除材料调差系数
- 字段名称:编码
- 备注:译码,编码
- 字段名称:计算式
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用编码
- 字段名称:路径
- 备注:路径,项目全路径
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|专业类型|人工调差系数|代码|单位|取费表|合价|名称|备注|序号|拆除人工调差系数|拆除机械调差系数|拆除材料调差系数|数量|机械调差系数|材料调差系数|编码|计算式|费率|费用编码|路径|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|余物清理|0||||0|建筑工程||1|0|0|0||0|0|||0||建筑工程|项目划分||{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{3D836341-C533-453A-BD87-D250D1D4AF0D}|余物清理|0|||线路取费表(余物清理)|0|一般砖木结构||1.1|0|0|0||0|0|||10||建筑工程/一般砖木结构|项目划分|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{34D75862-8A18-4529-B068-31484FCA64FB}|余物清理|0|||线路取费表(余物清理)|0|混合结构||1.2|0|0|0||0|0|||20||建筑工程/混合结构|项目划分|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{86BD93D9-3FBB-4364-AC13-E418CBBC6ED7}|余物清理|0||||0|混凝土及钢筋混凝土结构||1.3|0|0|0||0|0|||0||建筑工程/混凝土及钢筋混凝土结构|项目划分|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{5A6E98BD-3225-425B-BAB1-1EDB1DCBC296}|余物清理|0|||线路取费表(余物清理)|0|(1)有条件爆破的||1.3.1|0|0|0||0|0|||20||建筑工程/混凝土及钢筋混凝土结构/(1)有条件爆破的|项目划分|{86BD93D9-3FBB-4364-AC13-E418CBBC6ED7}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{3947BA59-7ED4-40E6-AADD-1E5D312E29CF}|余物清理|0|||线路取费表(余物清理)|0|(2)无条件爆破的|费率在30~50区间|1.3.2|0|0|0||0|0|||0||建筑工程/混凝土及钢筋混凝土结构/(2)无条件爆破的|项目划分|{86BD93D9-3FBB-4364-AC13-E418CBBC6ED7}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{9E603329-2793-4DA6-90BE-72BD2F4AF4F0}|余物清理|0|||线路取费表(余物清理)|0|临时简易建筑||1.4|0|0|0||0|0|||8||建筑工程/临时简易建筑|项目划分|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{81BE9F51-3D11-4C79-937D-021B8E7DFDFA}|余物清理|0||||0|金属结构||1.5|0|0|0||0|0|||0||建筑工程/金属结构|项目划分|{5A83B793-0E06-4C31-A90B-6FEBDCF6B21F}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{2D787869-888E-4666-8349-440E3584D2BE}|余物清理|0|||线路取费表(余物清理)|0|(1)拆除后能利用||1.5.1|0|0|0||0|0|||55||建筑工程/金属结构/(1)拆除后能利用|项目划分|{81BE9F51-3D11-4C79-937D-021B8E7DFDFA}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{720CB889-8A4B-49CB-9611-E4A75EA9B9BF}|余物清理|0|||线路取费表(余物清理)|0|(2)拆除后不能利用||1.5.2|0|0|0||0|0|||38||建筑工程/金属结构/(2)拆除后不能利用|项目划分|{81BE9F51-3D11-4C79-937D-021B8E7DFDFA}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{6BEAE0B5-CF26-4272-A59E-ADF990AA96EA}|余物清理|0||||0|安装工程||2|0|0|0||0|0|||0||安装工程|项目划分||{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{D26571BD-9C0D-4E04-B6CA-5B1618C7DCB4}|余物清理|0|||线路取费表(余物清理)|0|金属结构及工业管道||2.1|0|0|0||0|0|||45||安装工程/金属结构及工业管道|项目划分|{6BEAE0B5-CF26-4272-A59E-ADF990AA96EA}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{3FF3E035-8603-4B4C-BA81-3AF5FAA6902F}|余物清理|0|||线路取费表(余物清理)|0|机电设备||2.2|0|0|0||0|0|||32||安装工程/机电设备|项目划分|{6BEAE0B5-CF26-4272-A59E-ADF990AA96EA}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{FF9AC2CF-93F7-41CA-84ED-EB237580F77C}|余物清理|0||||0|输电线路及通信线路||2.3|0|0|0||0|0|||0||安装工程/输电线路及通信线路|项目划分|{6BEAE0B5-CF26-4272-A59E-ADF990AA96EA}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{FE1AC208-65B7-4DD5-AE8A-F563D07C2886}|余物清理|0|||线路取费表(余物清理)|0|(1)拆除后能利用||2.3.1|0|0|0||0|0|||62||安装工程/输电线路及通信线路/(1)拆除后能利用|项目划分|{FF9AC2CF-93F7-41CA-84ED-EB237580F77C}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
|{50AFD995-F0F1-45C9-BD0E-79F50F08D907}|余物清理|0|||线路取费表(余物清理)|0|(2)拆除后不能利用||2.3.2|0|0|0||0|0|||35||安装工程/输电线路及通信线路/(2)拆除后不能利用|项目划分|{FF9AC2CF-93F7-41CA-84ED-EB237580F77C}|{5FCB462B-727C-4E30-AC05-6F463CE1A707}|
@@ -0,0 +1,95 @@
# 项目划分_线路
备注:项目划分表是用于存储工程项目划分树状数据。内部包含安装工程项目划分,建筑工程项目划分,线路项目划分,工程分部分项。查询示例: SELECT Sum_Price FROM ProjectDivision WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:专业类型
- 备注:专业类型
- 字段名称:人工调差系数
- 备注:拆除人工调差系数
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:单位
- 字段名称:取费表
- 备注:取费表
- 字段名称:合价
- 备注:合价,合计
- 字段名称:名称
- 备注:项目名,名称
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:项目序号,序号,序列号
- 字段名称:拆除人工调差系数
- 备注:拆除人工调差系数
- 字段名称:拆除机械调差系数
- 备注:拆除机械调差系数
- 字段名称:拆除材料调差系数
- 备注:拆除材料调差系数
- 字段名称:数量
- 备注:数目,数量,个数
- 字段名称:机械调差系数
- 备注:拆除机械调差系数
- 字段名称:材料调差系数
- 备注:拆除材料调差系数
- 字段名称:编码
- 备注:译码,编码
- 字段名称:计算式
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用编码
- 字段名称:路径
- 备注:路径,项目全路径
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|专业类型|人工调差系数|代码|单位|取费表|合价|名称|备注|序号|拆除人工调差系数|拆除机械调差系数|拆除材料调差系数|数量|机械调差系数|材料调差系数|编码|计算式|费率|费用编码|路径|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|线路|9.58|BTGC|元/km||9753672.891356|架空输电线路本体工程||一|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程|项目划分||{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|线路|9.58|JCGC|元/m³||31501.175855|基础工程||1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{3C4DD6EF-29D9-4D99-8F28-0E49B651B1F0}|线路|9.58|||线路取费表|0|基础工程材料工地运输||1.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础工程材料工地运输|项目划分|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{8D99578D-6E1B-4EE0-AC93-5865C48EA52B}|线路|9.58|||线路取费表|31501.175855|基础土石方工程||1.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础土石方工程|项目划分|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|线路|9.58||||0|基础砌筑||1.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑|项目划分|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{3A4448BE-489D-4159-8B1C-B1863801B8D8}|线路|9.58|||线路取费表|0|预制基础||1.3.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑/预制基础|项目划分|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{0EB2CE2E-A911-4AAA-BCDB-E47B82CA093B}|线路|9.58|||线路取费表|0|现浇基础||1.3.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑/现浇基础|项目划分|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{DD1FE7A9-9246-45E8-A81B-1376F3EEFAEF}|线路|9.58|||线路取费表|0|灌注桩基础||1.3.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑/灌注桩基础|项目划分|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{ADF11384-A2A6-45E3-9984-FEB26D350ADD}|线路|9.58|||线路取费表|0|锚杆基础||1.3.4|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑/锚杆基础|项目划分|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{D5D04846-26E0-4F96-9E58-26BAEC39E6FD}|线路|9.58|||线路取费表|0|其他基础||1.3.5|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础砌筑/其他基础|项目划分|{8C30BE69-B9B5-4F12-B84D-E5E54CEAB3B3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{5B9D825B-A255-4638-9BA3-93B15267F808}|线路|9.58|||线路取费表|0|基础防护||1.4|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/基础防护|项目划分|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{9C79B49F-79ED-4DD5-B5BA-E3025A9500C5}|线路|9.58|||线路取费表|0|地基处理||1.5|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/基础工程/地基处理|项目划分|{A3FF093B-8710-47A9-B7EC-873FCC712F2D}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{0EE7BD7B-AB43-4422-99F1-04DD8AEAE108}|线路|9.58|GTGC|元/t||0|杆塔工程||2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/杆塔工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{8B2DFC9D-5041-4F69-BA32-E4FACC07EC72}|线路|9.58|||线路取费表|0|杆塔工程材料工地运输||2.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/杆塔工程/杆塔工程材料工地运输|项目划分|{0EE7BD7B-AB43-4422-99F1-04DD8AEAE108}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{B9388E51-A827-4E76-A75D-CB421B2D3FD3}|线路|9.58||||0|杆塔组立||2.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/杆塔工程/杆塔组立|项目划分|{0EE7BD7B-AB43-4422-99F1-04DD8AEAE108}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{E875B06B-27C0-475F-A6BA-F1F9B541C3D1}|线路|9.58|||线路取费表|0|混凝土杆组立||2.2.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/杆塔工程/杆塔组立/混凝土杆组立|项目划分|{B9388E51-A827-4E76-A75D-CB421B2D3FD3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{6C5C5DFB-2F86-4B3F-8636-1F99EE18AF8D}|线路|9.58|||线路取费表|0|铁塔、钢管杆组立||2.2.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/杆塔工程/杆塔组立/铁塔、钢管杆组立|项目划分|{B9388E51-A827-4E76-A75D-CB421B2D3FD3}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{09E6E78A-F5BE-4A09-A773-C2DC984CBDB7}|线路|9.58|JDGC|元/基||0|接地工程||3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/接地工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{04A67B95-6601-4DEB-8ADB-9F2D34EDE9AE}|线路|9.58|||线路取费表|0|接地工程材料工地运输||3.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/接地工程/接地工程材料工地运输|项目划分|{09E6E78A-F5BE-4A09-A773-C2DC984CBDB7}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{AA2724F1-6C40-41C0-B410-8CEFCC4DF6CC}|线路|9.58|||线路取费表|0|接地土石方||3.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/接地工程/接地土石方|项目划分|{09E6E78A-F5BE-4A09-A773-C2DC984CBDB7}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{23DA6FFE-4741-4C5C-B0CD-73A899CEC0BF}|线路|9.58|||线路取费表|0|接地安装||3.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/接地工程/接地安装|项目划分|{09E6E78A-F5BE-4A09-A773-C2DC984CBDB7}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{89D90768-FC57-42AC-BACA-63FA036FF403}|线路|9.58|JXGC|元/km||0|架线工程||4|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/架线工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{A839D9B4-29F9-4B67-8260-17B18604FBC1}|线路|9.58|||线路取费表|0|架线工程材料工地运输||4.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/架线工程/架线工程材料工地运输|项目划分|{89D90768-FC57-42AC-BACA-63FA036FF403}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{D6EB7E76-F087-44FE-84E0-34A381FCEA9C}|线路|9.58|||线路取费表|0|导地线架设||4.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/架线工程/导地线架设|项目划分|{89D90768-FC57-42AC-BACA-63FA036FF403}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{0B9F3695-666B-4170-A0C5-77AE78DD2C56}|线路|9.58|||线路取费表|0|导地线跨越架设||4.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/架线工程/导地线跨越架设|项目划分|{89D90768-FC57-42AC-BACA-63FA036FF403}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{E3CCEA65-FA05-4279-B245-A94281E2D7C3}|线路|9.58|||线路取费表|0|其他架线工程||4.4|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/架线工程/其他架线工程|项目划分|{89D90768-FC57-42AC-BACA-63FA036FF403}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{6CE37565-7D19-444C-839E-4C70E5EC3A15}|线路|9.58|FJAZ|元/基||0|附件安装工程||5|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/附件安装工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{AE084DF5-531C-46DC-A443-1BA402C85260}|线路|9.58|||线路取费表|0|附件安装工程材料工地运输||5.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/附件安装工程/附件安装工程材料工地运输|项目划分|{6CE37565-7D19-444C-839E-4C70E5EC3A15}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{E48B1BE7-4463-4552-86AC-4E787E440862}|线路|9.58||||0|绝缘子串及金具安装||5.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/附件安装工程/绝缘子串及金具安装|项目划分|{6CE37565-7D19-444C-839E-4C70E5EC3A15}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{A2AB1180-EB03-452F-8EB3-4D2EBB200058}|线路|9.58|||线路取费表|0|耐张绝缘子串及金具安装||5.2.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/附件安装工程/绝缘子串及金具安装/耐张绝缘子串及金具安装|项目划分|{E48B1BE7-4463-4552-86AC-4E787E440862}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{44BEF6A2-684A-4179-9CD3-D46FC66E819E}|线路|9.58|||线路取费表|0|悬垂绝缘子串及金具安装||5.2.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/附件安装工程/绝缘子串及金具安装/悬垂绝缘子串及金具安装|项目划分|{E48B1BE7-4463-4552-86AC-4E787E440862}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{432AFE7A-E069-43A8-951D-583A280D2913}|线路|9.58|FZGC|元/km、元/m³、元/处||0|辅助工程||6|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{81762019-097C-4C0B-8DD5-EBC3446089FD}|线路|9.58|||线路取费表|0|尖峰、施工基面土石方工程||6.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/尖峰、施工基面土石方工程|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{89CA1CA6-44FF-4EF1-B155-1EDC8096BA19}|线路|9.58||||0|护坡、挡土墙及排洪沟||6.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/护坡、挡土墙及排洪沟|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{CFD85CF6-A6F7-49EA-B608-29E58BC41CD8}|线路|9.58|||线路取费表|0|护坡、挡土墙及排洪沟材料工地运输||6.2.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟材料工地运输|项目划分|{89CA1CA6-44FF-4EF1-B155-1EDC8096BA19}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{2DC4FFAB-F3BF-4843-A8AF-050B7FBD1830}|线路|9.58|||线路取费表|0|护坡、挡土墙及排洪沟土石方工程||6.2.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟土石方工程|项目划分|{89CA1CA6-44FF-4EF1-B155-1EDC8096BA19}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{846B357D-9D64-4DCF-A14F-43F358730567}|线路|9.58|||线路取费表|0|护坡、挡土墙及排洪沟砌筑||6.2.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/护坡、挡土墙及排洪沟/护坡、挡土墙及排洪沟砌筑|项目划分|{89CA1CA6-44FF-4EF1-B155-1EDC8096BA19}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{59586B2B-E3BD-4827-9015-2A8C218B6904}|线路|9.58||||0|基础永久性围堰||6.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/基础永久性围堰|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{178CE9DB-2CD8-4FAF-942C-D23CACB991DE}|线路|9.58|||线路取费表|0|基础永久性围堰材料工地运输||6.3.1|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰材料工地运输|项目划分|{59586B2B-E3BD-4827-9015-2A8C218B6904}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{F0884993-7E6E-4BC6-9D7F-CAAB3EA261CB}|线路|9.58|||线路取费表|0|基础永久性围堰土石方工程||6.3.2|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰土石方工程|项目划分|{59586B2B-E3BD-4827-9015-2A8C218B6904}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{674D665F-AA82-4E9F-82F5-78BF4A31B6F7}|线路|9.58|||线路取费表|0|基础永久性围堰砌筑||6.3.3|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/基础永久性围堰/基础永久性围堰砌筑|项目划分|{59586B2B-E3BD-4827-9015-2A8C218B6904}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{C4429A35-FFD9-4FDB-A395-69A2672ED2D6}|线路|9.58|||线路取费表|0|索道站安装||6.4|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/索道站安装|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{8F3F9C27-9354-4DC3-AFB4-36603FF20B2E}|线路|9.58|||线路取费表|0|杆塔上装的各类辅助生产装置||6.5|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/杆塔上装的各类辅助生产装置|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{1B689340-80BC-48EB-A79B-D8D9AF7FD1F6}|线路|9.58|||线路取费表|0|输、送电线路试运||6.6|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/辅助工程/输、送电线路试运|项目划分|{432AFE7A-E069-43A8-951D-583A280D2913}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{F8F0651B-2077-433B-8E3E-F8A441F4AEC2}|线路|9.58|||线路取费表|0|电缆工程||7|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/电缆工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{D13C3D5D-A38E-4B0E-B3B4-630FB8904A33}|线路|9.58|||线路取费表|0|通信线路工程||8|7.69|5.75|5.75||6.2|6.2|||0||架空输电线路本体工程/通信线路工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
|{3824000E-A0BA-42F9-9957-55FE9B4CF367}|线路|9.58|QTGC||线路取费表|9722171.715501|其他线路工程||9|7.69|5.75|5.75||6.2|6.2|01||0||架空输电线路本体工程/其他线路工程|项目划分|{9A7491C5-DF31-4228-BB86-1B0982D1C512}|{69305240-E6E2-4ADD-B48C-AF6E199D1AD5}|
@@ -0,0 +1,82 @@
# 其他费用
备注:其他费用表被称为“工程费用中其他费用明细”。其他费用是指为完成工程项目建设所必需的,但不属于建筑工程费、安装工程费、设备购置费、基本预备费的其他相关费用。包括建设场地征用及清理费、项目建设管理费、项目建设技术服务费、生产准备费、大件运输措施费、专业爆破服务费等。查询示例: SELECT Rate FROM OtherFee WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:nodeType
- 字段名称:relTbId
- 字段名称:parentId
- 字段名称:序号
- 备注:序号,序列号
- 字段名称:名称
- 备注:项目名,费用名,名称
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:单位
- 备注:金额,价格
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:金额
- 备注:金额,价格
- 字段名称:编码
- 备注:WBS编号,WBS编码
- 字段名称:服务内容
- 字段名称:费用归属
- 字段名称:输出
- 字段名称:不可竞争费用
- 字段名称:编制依据
- 备注:编制依据,编制来源
- 字段名称:备注
- 备注:备注,说明
- 字段名称:表一显示
- 字段名称:税率
|_id|nodeType|relTbId|parentId|序号|名称|代码|单位|取费基数|费率|金额|编码|服务内容|费用归属|输出|不可竞争费用|编制依据|备注|表一显示|税率|
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|31yqbmpfp3b4|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||1|建设场地征用及清理费|A||建设场地征用及清理费|100|25282.5|41831000000|||否|否|||是|0|
|31yqbmpi6znk|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||2|项目建设管理费|B|||100|183066.715962|41832000000|||否|否|||否|0|
|31yqbmpi6znl|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.1|项目法人管理费|B1||(建筑工程费+安装工程费+建筑基准期价差+安装基准期价差)*0.8|3.35|65590.7485|41832100000|||否|否|||否|0|
|31yqbmpi6znm|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.2|招标费|B2||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|1.24|30347.958261|41832200000|||否|否||线路长度超过500km时,超过部分每增加100km,费率乘以0.92系数 |否|6|
|31yqbmpkow00|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.3|工程监理费|B3||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|3.1|75869.895653|41832300000|||否|否||说明:162号文指导费率区间:2.71%-2.73%;35kV及以上箱式变电站按每站1.5-3.5万元计列。|否|6|
|31yqbmpkow01|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.4|设备材料监造费|B4||监造材料费|0|0|41832400000|||否|否|||否|6|
|31yqbmpkow02|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.5|施工过程造价咨询及竣工结算审核费|B5||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0.46|11258.113548|41832500000|||否|否||费用计算低于3000元时,按3000元计列。|否|6|
|31yqbmpn6scg|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpi6znk|2.6|工程保险费|B6|||100|0|41832600000|||否|否|||否|6|
|31yqbmpn6sch|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||3|项目建设技术服务费|C|||100|463215.689047|41833000000|||否|否|||否|6|
|31yqbmpn6sci|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.1|项目前期工作费|C1||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0.94|23005.710295|41833100000|||否|否|||否|6|
|31yqbmppooow|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.1|可行性研究费用|C11|||100|0|41833110000|||否|否||说明:162号文指导费用区间:12万元-20万元;20km以上,增加0.5万元/km;多回路、高海拔等可调整。|否|6|
|31yqbmppooox|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.2|环境影响评价费用|C12|||100|0|41833120000|||否|否||说明:162号文指导费用区间:5万元-8万元;20km以上,增加0.25万元/km;穿越环境敏感区、平行走廊等可调整。|否|6|
|31yqbmppoooy|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.3|建设项目规划选址费|C13|||100|0|41833130000|||否|否||说明:162号文指导费用区间:3万元-10万元;20km以上,增加0.1万元/km;平行走廊等可调整。|否|6|
|31yqbmppoooz|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.4|水土保持方案编审费用|C14|||100|0|41833140000|||否|否||说明:162号文指导费用区间:3万元-6万元;20km以上,增加0.2万元/km;平行走廊等可调整。|否|6|
|31yqbmps6l1c|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.5|地质灾害危险性评估费用|C15|||100|0|41833150000|||否|否||说明:162号文指导费用区间:2万元-3万元;20km以上,增加0.15万元/km;平行走廊等可调整。|否|6|
|31yqbmps6l1d|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.6|地震安全性评价费用|C16|||100|0|41833160000|||否|否||说明:线路工程原则上不计此费用|否|6|
|31yqbmps6l1e|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.7|文物调查费用|C17|||100|0|41833170000|||否|否||说明:162号文指导费用区间:3万元-8万元;20km以上,增加0.05-0.15万元/km;平行走廊等可调整。|否|6|
|31yqbmpuohds|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.8|矿产压覆评估费用|C18|||100|0|41833180000|||否|否||说明:162号文指导费用区间:4万元-8万元;20km以上,增加0.1-0.3万元/km;平行走廊等可调整。|否|6|
|31yqbmpuohdt|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.9|用地预审费用|C19|||100|0|41833190000|||否|否||说明:162号文指导费用区间:5万元-12万元;20km以上,增加0.1-0.3万元/km;平行走廊等可调整。|否|6|
|31yqbmpuohdu|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.10|节能评估费用|C1A|||100|0|418331A0000|||否|否||说明:162号文指导费用区间:2万元-5万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31yqbmpx6dq8|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.11|社会稳定风险评估费用|C1B|||100|0|418331B0000|||否|否||说明:162号文指导费用区间:5万元-10万元;20km以上,增加0.01-0.05万元/km;平行走廊等可调整。|否|6|
|31yqbmpx6dq9|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.12|使用林地可行性研究费用|C1C|||100|0|418331C0000|||否|否||说明:162号文指导费用区间:3万元-5万元;20km以上,增加0.1万元/km。|否|6|
|31yqbmpzoa2o|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sci|3.1.13|前期工作管理费用|C1D|||100|0|418331D0000|||否|否||说明:162号文指导费用:10万元;单独的变电站、换流站、输电线路工程按40%-60%调整|否|6|
|31yqbmpzoa2p|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.2|知识产权转让与研究试验费|C2|||100|0|41833200000|||否|否||根据建设项目法人提出的项目和费用计列。|否|6|
|31yqbmpzoa2q|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.3|勘察设计费|C3|||100|429686.09|41833300000|||否|否|||否|6|
|31yqbmpzoa2r|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpzoa2q|3.3.1|勘察费|C31||勘察费|100|219018.33|41833310000|||否|否|||否|6|
|31yqbmq266f4|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpzoa2q|3.3.2|设计费|C32||设计费|100|210667.76|41833320000|||否|否|||否|6|
|31yqbmq266f5|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.4|设计文件评审费|C4|||100|0|41833400000|||否|否|||否|6|
|31yqbmq266f6|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq266f5|3.4.1|可行性研究文件评审费|C41||可行性研究评审费|0|0|41833410000|||否|否|||否|6|
|31yqbmq4o2rk|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq266f5|3.4.2|初步设计文件评审费|C42||初步设计评审费|0|0|41833420000|||否|否|||否|6|
|31yqbmq75z40|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq266f5|3.4.3|施工图文件评审费|C43||施工图评审费|0|0|41833430000|||否|否|||否|6|
|31yqbmq75z41|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.5|项目后评价费|C5||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0|0|41833500000|||否|否||单项输变电工程,建筑工程费+安装工程费低于2000万元,取费基数取2000万元。|否|6|
|31yqbmq9nvgg|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.6|工程建设检测费|C6|||100|8076.472763|41833600000|||否|否|||否|6|
|31yqbmq9nvgh|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq9nvgg|3.6.1|电力工程质量检测费|C61||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0.33|8076.472763|41833610000|||否|否|||否|6|
|31yqbmq9nvgi|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq9nvgg|3.6.2|特种设备安全监测费|C62|||100|0|41833620000|||否|否|||否|6|
|31yqbmq9nvgj|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq9nvgg|3.6.3|环境监测及环境保护验收费|C63|||100|0|41833630000|||否|否|||否|6|
|31yqbmqc5rsw|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq9nvgg|3.6.4|水土保持监测及验收费|C64|||100|0|41833640000|||否|否|||否|6|
|31yqbmqc5rsx|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmq9nvgg|3.6.5|桩基检测费|C65|||100|0|41833650000|||否|否|||否|6|
|31yqbmqc5rsy|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmpn6sch|3.7|电力工程技术经济标准编制费|C7||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0.1|2447.415989|41833700000|||否|否|||否|6|
|31yqbmqc5rsz|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||4|生产准备费|D|||100|45784.837568|41834000000|||否|否|||否|0|
|31yqbmqeno5c|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmqc5rsz|4.1|管理车辆购置费|D1||设备购置费|0.75|18373.778493|41834100000|||否|否||注:如果管理车辆由项目法人单位统一配置,并且不在工程项目中分摊相关费用时,本项费用不计。|否|13|
|31yqbmqeno5d|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmqc5rsz|4.2|工器具及办公家具购置费|D2||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|1.07|26187.35108|41834200000|||否|否|||否|13|
|31yqbmqeno5e|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmqc5rsz|4.3|生产职工培训及提前进场费|D3||建筑工程费+安装工程费+建筑基准期价差+安装基准期价差|0.05|1223.707994|41834300000|||否|否|||否|0|
|31yqbmqh5khs|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||5|专业爆破服务费|E|||100|0|41835000000|||否|否|||否|0|
|31yqbmqjngu8|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}||6|其他|F|||100|18000|41836000000|||否|否|||否|0|
|31yqbmqjngu9|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmqjngu8|6.1|白蚁防治费|||360*50|100|18000|41836100000|||否|否|||否|0|
|31yqbmqjngua|其他费用|{3A3B6448-D486-4D0C-8074-28554CD36003}|31yqbmqjngu8|6.2|余土消纳费|||(1182.96+33.66+549.575)*15*0|100|0|41836200000|||否|否|||否|0|
@@ -0,0 +1,29 @@
# 大型土石方取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{0552C4D6-A240-43D7-87E7-459F6AE73E96}|FFZ1|||一|否|100|直接工程费|取费表||{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{26103E34-3F0C-412B-AAA5-C94AA076C6F9}|RGF|取费定额人工费||1|否|100|人工费|取费表|{0552C4D6-A240-43D7-87E7-459F6AE73E96}|{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{6F6328CA-D4D9-483C-85E9-D711CE0BB952}|CLF|取费定额乙供材料费不含税+取费定额甲供材料费含税+乙供取费主材费不含税+甲供取费主材费含税||2|否|100|材料费|取费表|{0552C4D6-A240-43D7-87E7-459F6AE73E96}|{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{6D3985D1-998B-45DA-8BF5-CEA701D55488}|JXF|取费定额机械费||3|否|100|施工机械使用费|取费表|{0552C4D6-A240-43D7-87E7-459F6AE73E96}|{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{54F88EF2-20E5-4D27-8A44-A486B15EABCC}|TZHQF|FFZ1-甲供消材进项税额-甲供主材进项税额|综合取费费用额(包含措施费、间接费、利润)|二|否|17.79|综合取费费用额|取费表||{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{774F581D-FD7C-468E-9E3C-4794C4566764}|TFFS|FFZ1+TZHQF-取费定额甲供材料费含税-甲供取费主材费含税+不取费定额费不含税-不取费甲供材料费不含税+不取费乙供主材费不含税||三|否|9|税金|取费表||{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
|{EC65C030-D4EC-4AB1-8BB5-D76F494B903C}|THJ|FFZ1+TZHQF+TFFS+一笔性费用+不取费定额费不含税+不取费乙供主材费不含税+不取费甲供材料进项税额+不取费甲供主材费含税||四|否|100|合计|取费表||{5714D95B-6C68-4D36-B406-6A564D9CA88F}|
@@ -0,0 +1,53 @@
# 安装取费表_取费表
备注:取费表是取费设置中各取费表明细。查询示例: SELECT Rate FROM FeeCollectionTable WHERE Name = 'findname'。
- 字段名称:_id
- 字段名称:代码
- 备注:编号,代码,代号
- 字段名称:取费基数
- 备注:公式,计算式,表达式
- 字段名称:备注
- 备注:备注,说明
- 字段名称:序号
- 备注:费用序号,序号,序列号
- 字段名称:是否隐藏
- 字段名称:费率
- 备注:费用利率,费率
- 字段名称:费用名称
- 备注:项目名,费用名,名称
- 字段名称:nodeType
- 字段名称:parentId
- 字段名称:relTbId
|_id|代码|取费基数|备注|序号|是否隐藏|费率|费用名称|nodeType|parentId|relTbId|
|---|---|---|---|---|---|---|---|---|---|---|
|{528A23DF-84DF-4A5B-A4F7-3C36946DF10A}|FFZ|||一|否|100|直接费|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{75484B7F-B129-41AC-AC84-951103432A04}|FFZ1|||1|否|100|直接工程费|取费表|{528A23DF-84DF-4A5B-A4F7-3C36946DF10A}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{17192AC1-6F06-4105-98DB-50AAE16FC96D}|DZF|||1.1|否|100|定额直接费|取费表|{75484B7F-B129-41AC-AC84-951103432A04}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{2E0927DF-D1FB-4887-BCD5-843795984C8B}|RGF|取费定额人工费||1.1.1|否|100|人工费|取费表|{17192AC1-6F06-4105-98DB-50AAE16FC96D}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{3F14A3F1-592D-4DAA-AEF6-D77189EEA27B}|CLF|取费定额乙供材料费不含税||1.1.2|否|100|材料费|取费表|{17192AC1-6F06-4105-98DB-50AAE16FC96D}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{18BCC5DA-CF04-4A18-A212-8224412370DC}|JXF|取费定额机械费||1.1.3|否|100|施工机械使用费|取费表|{17192AC1-6F06-4105-98DB-50AAE16FC96D}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{77E89796-F47F-4764-B025-C9DDFD66F7A8}|ZZCF|||1.2|否|100|装置性材料费|取费表|{75484B7F-B129-41AC-AC84-951103432A04}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{3EB92E69-6132-42B6-B337-E8719BD3C514}|JZZCF|甲供取费主材费含税||1.2.1|否|100|甲供装置性材料费|取费表|{77E89796-F47F-4764-B025-C9DDFD66F7A8}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{70487150-31DD-492F-9800-81BFC2E4785A}|YZZCF|乙供取费主材费不含税||1.2.2|否|100|乙供装置性材料费|取费表|{77E89796-F47F-4764-B025-C9DDFD66F7A8}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{B46790E9-FCEB-47B6-955D-7607B48B5852}|FFZ2|||2|否|100|措施费|取费表|{528A23DF-84DF-4A5B-A4F7-3C36946DF10A}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{A74A4ACD-0A40-4E60-8181-61E0C321E0CB}|DYF|取费定额人工费||2.1|否|2.76|冬雨季施工增加费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{F048D93A-A7F9-442F-A8B7-C60B8920706E}|YSF|DZF||2.2|否|0.61|夜间施工增加费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{45914735-E941-4AD3-B34B-8B57EF794A5E}|SYF|取费定额人工费||2.3|否|3.72|施工工具用具使用费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{A1EF2086-2D48-43CF-A0CF-30EE0D70E2C2}|TDF|取费定额人工费||2.4|否|0|特殊地区施工增加费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{1D26BA7A-9B13-410F-AF86-124DD5D5369A}|LSF|DZF||2.5|否|11.96|临时设施费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{8C5B56B8-1235-488D-BBBC-FCB872EE4592}|ZYF|取费定额人工费||2.6|否|1.64|施工机构迁移费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{F6A33651-2AEE-4283-BBC9-0CE08B866C1E}|BZF|FFZ1-甲供主材进项税额||2.7|否|3.25|安全文明施工费|取费表|{B46790E9-FCEB-47B6-955D-7607B48B5852}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{6F501364-0378-4CCB-9A04-BE6340B19991}|FFJ|||二|否|100|间接费|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{7212DD7F-FFC7-498F-BFE4-20A63ECA49D8}|GF|||1|否|100|规费|取费表|{6F501364-0378-4CCB-9A04-BE6340B19991}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{3C4A6C2B-42D4-4CC1-982E-9C76DC96F733}|BZHF|取费定额人工费*1.07||1.1|否|22.78|社会保险费|取费表|{7212DD7F-FFC7-498F-BFE4-20A63ECA49D8}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{B8673C1F-7F8F-4A36-8008-8A82AC9A0622}|GJJ|取费定额人工费*1.07||1.2|否|12|住房公积金|取费表|{7212DD7F-FFC7-498F-BFE4-20A63ECA49D8}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{457FB6CD-B6F4-4DDF-B4A0-F4CAD491612E}|GLF|取费定额人工费||2|否|38.25|企业管理费|取费表|{6F501364-0378-4CCB-9A04-BE6340B19991}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{61A369DF-8125-4BF1-88D9-A63CBBCE7845}|FFR|FFZ+FFJ-甲供主材进项税额||三|否|5|利润|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{A5F09649-F305-4436-B7AF-288CB99F0794}|FFS|FFZ+FFJ+FFR-甲供取费主材费含税+不取费定额费不含税+不取费乙供主材费不含税||四|否|9|税金|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{C5DAB4C1-1654-4401-80FB-223F90D96C85}|SBF|||五|否|100|设备费|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{47015E81-839B-42CD-A9CF-E754BA553820}|SBY|乙供设备费不含税+乙供设备税金||1|否|100|乙供设备不含税价|取费表|{C5DAB4C1-1654-4401-80FB-223F90D96C85}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{1F498CC3-FE40-4136-83E8-1E32F8D9E3D0}|SBJ|甲供设备费含税||2|否|100|甲供设备含税价|取费表|{C5DAB4C1-1654-4401-80FB-223F90D96C85}|{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{F62B9907-1D45-4B09-BE14-0E28010C0CF3}|AZF|DZF+FFZ2+FFJ+FFR+FFS+不取费定额费不含税+一笔性费用||六|否|100|安装费|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{E6E222E9-67B4-474D-AEB3-10F0191B04B9}|ZCF|ZZCF+不取费乙供主材费不含税+不取费甲供主材费含税||七|否|100|主材费|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{0398F2A8-7BED-49F9-8EF1-79C0C28DA7D9}|ZJ|AZF+ZCF+SBF||八|否|100|总计|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|
|{8C5B0866-AF80-42ED-82E0-AE5E17703DCC}|HJ|ZJ-SBF||九|否|100|合计|取费表||{5B1AC3D7-E59C-4AB2-8350-8A9D1649E2CE}|

Some files were not shown because too many files have changed in this diff Show More