Blog

  • tdt4242-agreelance

    Agreelance group 12

    Heroku pipeline status License

    The best way to agree on the price of your freelancing jobs!

    Application available at: https://agreelance-group12.herokuapp.com

    Users

    Username Password Description
    Bjarte SwokT2!5LoSf Superuser status
    Eirik SwokT2!5LoSf
    Seb SwokT2!5LoSf

    Git flow

    We use the following branching strategy in this project

    Master Branch: master

    We consider master to be the main branch where the source code of HEAD always reflects a stable application. This is the branch from which all feature branches are forked, and into which all feature branches are merged.

    Changes to master should always come through a pull request!

    Feature Branches: feature-*

    Feature branches are used to develop new features. The essence of a feature branch is that it exists as long as the feature is in development, but will eventually be merged back into master (to definitely add the new feature to the upcoming release) or discarded (in case of a disappointing experiment).

    Feature branches should not exist in origin for very long. They should be merged into master, via pull request, as quickly as possible and then cleaned up.

    • Naming convention: feature-*
    • Branches from: master
    • Must merge back into: master

    Code and structure

    • agreelance/ django project folder containing the project modules
      • core/ contains all the project templates
        • index.html One of the project templates that uses a template language to insert if, loops and variables into html.
      • home/ user profile – overview over user projects
        • static/ – contains static files like js and images
        • templatetags/ folder containing template tags. Methods you import into your templates. Can be used in combination with views.
        • admins.py – file contaning definitions to connect models to the django admin panel
        • urls.py – contains mapping between urls and views
        • models.py – contains data models
        • tests/ – contains tests for the module. View Testing in Django for more.
        • views.py – Controller in MVC. Methods for rendering and accepting user data
        • forms.py – defenition of forms. Used to render html forms and verify user input
      • payment/ – module handling payment
      • projects/ – The largest module of the project containing code for creating project and tasks. Upload files, view files, adding roles and user to roles.
      • agreelance/ – The projects main module contaning settings.
      • static/ – common static files
      • user/ – module extending django’s user model with a profile contaning more information about the user.
      • manage.py – entry point for running the project.
      • seed.json – contains seed data for the project to get it up and running quickly

    Get started

    It’s reccomended to have a look at: https://www.djangoproject.com/start/

    Basic tutorial that walks trough what the different files do. https://docs.djangoproject.com/en/2.0/intro/tutorial01/

    Create a virtualenv https://docs.python-guide.org/dev/virtualenvs/

    Local setup

    Installation with examples for ubuntu. Windows and OSX is mostly the same

    Fork the project and clone it to your machine.

    Setup and activation of virtualenv (env that prevents python packages from being installed globaly on the machine)

    Naviagate into the project folder.

    pip install virtualenv

    virtualenv env

    For mac/linux:

    source env/bin/activate

    For windows:

    env\Scripts\activate.bat

    If you get an error related to charmap on Windows, run this command: set PYTHONIOENCODING=UTF-8

    Install python requirements

    pip install -r requirements.txt

    Note: Mac users may get an error related to psycopg2. To fix this try running:

    pip install psycopg2==2.7.5

    Migrate database

    python manage.py migrate

    Create superuser

    Create a local admin user by entering the following command:

    python manage.py createsuperuser

    Only username and password is required

    Start the app

    python manage.py runserver

    Add initial data

    You can add initial data either by going to the url the app is running on locally and adding /admin to the url.

    Add some categories and you should be all set.

    Or by entering

    python manage.py loaddata seed.json

    Email

    Copy agreelance/local_settings_example.py to agreelance/local_settings.py and replace the email placeholder values with values dscribes in the email section later in the instructions.

    To support sending of email you will have to create a gmail account and turn on less secure apps. Do not use your own email as Google might lock the account. See https://support.google.com/accounts/answer/6010255?hl=en for instructions for turning on less secure apps.

    To get email working on heroku you might have to visit https://accounts.google.com/DisplayUnlockCaptcha and click continue as the heroku server is in another location and Google thinks it is a hacking attempt.

    Continuous integration

    Continuous integration will build the code pushed to master and push it to your heroku app so you get a live version of your latest code by just pushing your code to GitLab.

    1. Fork the project at GitLab
    2. Create a heroku account and an app.
    3. Set the project in the .gitlab-cs.yml file by replacing <Your-herokuproject-name> with the name of the Heroku app you created - dpl --provider=heroku --app=<Your-herokuproject-name> --api-key=$HEROKU_STAGING_API_KEY
    4. Set varibles at GitLab
      • settings > ci > Environment Variables
      • HEROKU_STAGING_API_KEY = heroku > Account Settings > API Key
    5. Add heroku database
      • Resources > Add ons > search for postgres > add first option
    6. Set variables at heroku. Settings > Config vars > Reveal vars
      • DATABASE_URL = Should be set by default. If not here is where you can find it: Resources > postgress > settings > view credentials > URI
      • EMAIL_HOST_PASSWORD email password. Not mandatory if you do not want to send email
      • EMAIL_HOST_USER email adress. Not mandatory if you do not want to send email
      • IS_HEROKU = IS_HEROKU
    7. On GitLab go to CI / CD in the repository menu and select Run Pipeline if it has not already started. When both stages complete the app should be available on heroku. Staging will fail from timeout as Heroku does not give the propper response to end the job. But the log should state that the app was deployed.
    8. Setup the applications database.
    • Install heroku CLI by following: https://devcenter.heroku.com/articles/heroku-cli
    • Log in to the Heroku CLI by entering heroku login. This opens a webbrowser and you accept the login request.
    • Migrate database by entering heroku run python manage.py migrate -a <heroku-app-name>. Heroku run will run the folowing command on your heroku instance. Remember to replace <heroku-app-name> with your app name
    • and create an admin account by running heroku run python manage.py createsuperuser -a <heroku-app-name>.
    • seed database heroku run python manage.py loaddata seed.json -a <heroku-app-name>

    Reset Database

    heroku pg:reset DATABASE_URL -a <heroku-app-name>

    Data seeding

    The data seed provided contains 3 users, described in Users section above

    Visit original content creator repository https://github.com/maattss/tdt4242-agreelance
  • onedionys-analytics-integration

    Welcome to One Dionys – Analytics Integration! 👋

    Functions for integrating analytics tools such as Google Analytics into web applications. 💖

    💾 Requirements

    • Web Browser – Can be used as an emulator to build applications. Example [Chrome, Firefox, Safari & Opera].
    • Internet – Because many use CDN and to make it easier to find solutions to all problems.

    🎯 How To Use

    Example Syntax

    const { trackEvent } = require('./src/analytics');
    
    // Example usage
    const eventName = 'Button Click';
    const eventData = { buttonId: 'btnSubmit', page: 'homepage' };
    
    // Send event data to analytics service
    trackEvent(eventName, eventData);

    Explanation

    • This package provides a simple way to integrate analytics tracking into your application. The trackEvent function allows you to send custom event data to your analytics service, such as Google Analytics, to track user interactions, button clicks, page views, etc.

    Return Value

    • The trackEvent function does not return any value directly. It sends the event data to the analytics service. In the example provided above, it logs the event data to the console for demonstration purposes. However, in a real-world scenario, it would send the data to the configured analytics service.

    📆 Release Date

    • v1.0.0 : 08 March 2024
    • v1.0.1 : 11 March 2024
    • v4.0.0 : 11 March 2024
    • v4.0.1 : 13 March 2024
    • v4.0.2 : 18 March 2024
    • v5.0.0 : 31 March 2024

    🧑 Author

    📝 License

    • Copyright © 2024 One Dionys
    • One Dionys – Analytics Integration is an open source project licensed under the MIT license

    ☕️ Suppport & Donation

    Love One Dionys – Analytics Integration? Support this project by donating or sharing with others in need.

    Made with ❤️ One Dionys

    Visit original content creator repository https://github.com/onedionys/onedionys-analytics-integration
  • onedionys-analytics-integration

    Welcome to One Dionys – Analytics Integration! 👋

    Functions for integrating analytics tools such as Google Analytics into web applications. 💖

    💾 Requirements

    • Web Browser – Can be used as an emulator to build applications. Example [Chrome, Firefox, Safari & Opera].
    • Internet – Because many use CDN and to make it easier to find solutions to all problems.

    🎯 How To Use

    Example Syntax

    const { trackEvent } = require('./src/analytics');
    
    // Example usage
    const eventName = 'Button Click';
    const eventData = { buttonId: 'btnSubmit', page: 'homepage' };
    
    // Send event data to analytics service
    trackEvent(eventName, eventData);

    Explanation

    • This package provides a simple way to integrate analytics tracking into your application. The trackEvent function allows you to send custom event data to your analytics service, such as Google Analytics, to track user interactions, button clicks, page views, etc.

    Return Value

    • The trackEvent function does not return any value directly. It sends the event data to the analytics service. In the example provided above, it logs the event data to the console for demonstration purposes. However, in a real-world scenario, it would send the data to the configured analytics service.

    📆 Release Date

    • v1.0.0 : 08 March 2024
    • v1.0.1 : 11 March 2024
    • v4.0.0 : 11 March 2024
    • v4.0.1 : 13 March 2024
    • v4.0.2 : 18 March 2024
    • v5.0.0 : 31 March 2024

    🧑 Author

    📝 License

    • Copyright © 2024 One Dionys
    • One Dionys – Analytics Integration is an open source project licensed under the MIT license

    ☕️ Suppport & Donation

    Love One Dionys – Analytics Integration? Support this project by donating or sharing with others in need.

    Made with ❤️ One Dionys

    Visit original content creator repository https://github.com/onedionys/onedionys-analytics-integration
  • Protoinject

    Protoinject

    A hierarchical dependency injection system

    Protoinject is a hierarchical dependency injection system. Unlike conventional dependency injection libraries which only concern themselves with the resolution of services, Protoinject manages the lifecycle of services and associated them into a hierarchy of objects.

    This model allows Protoinject to seperate planning, verification and resolution of dependencies, allowing for many new scenarios such as:

    • Caching the planning results from the startup of your application, resulting in faster startup times.
    • Validating that all dependencies can be satisified before any objects are created, ensuring no side-effects occur if a request can not be satisified.
    • Creating custom plans from external sources, such as game levels. This allows you to verify that all objects in a scene have their dependencies satisified.
    • Navigating and querying the hierarchy at runtime, which maps extremely well to entity-component systems.

    Getting Started

    Protoinject is commonly used within Protogame. If you’re already using Protogame, then you don’t need to manually install this library; it is already available to you.

    If you are not using Protogame, or you want to use Protoinject for general application purposes, you can install Protoinject into your project using Protobuild, like so:

    Protobuild.exe --install https://protobuild.org/hach-que/Protoinject
    

    Then reference Protoinject from your project, like so:

    Copyright (c) 2015 Redpoint Games Pty Ltd
    
    Permission is hereby granted, free of charge, to any person obtaining a copy
    of this software and associated documentation files (the "Software"), to deal
    in the Software without restriction, including without limitation the rights
    to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
    copies of the Software, and to permit persons to whom the Software is
    furnished to do so, subject to the following conditions:
    
    The above copyright notice and this permission notice shall be included in
    all copies or substantial portions of the Software.
    
    THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
    IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
    FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE
    AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
    LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
    OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
    THE SOFTWARE.
    

    Community Code of Conduct

    This project has adopted the code of conduct defined by the Contributor Covenant to clarify expected behavior in our community. For more information see the .NET Foundation Code of Conduct.

    Visit original content creator repository https://github.com/RedpointArchive/Protoinject
  • sol-sniper-bot

    Intro

    This bot allows you to automate your crypto trading strategies on the Solana blockchain. The bot is currently written in JS and uses the Raydium V2 SDK to execute trades.
    Basic logics here is listen new pool created in Raydium AMM and if that token matches the filter sets based on the predefined parameters, it executes strategies set by the user.
    Simply the bot will periodity calculate the price and if it hits TP/SL or the PRICE_CHECK_DURATION timedout – bot will sell the token
    (Because there are many rugged pull here, it’s better to sell tokens before the liquidity is too low, when the amoutOut is too small you can not sell that token anymore, or can’t redeem the rental fee 0.002 SOL by default);

    NO REFERAL FEE

    ❗❗This code doesn’t include or require your fee per transaction. Feel free to use as your own.

    Disclaimer

    🛑 This bot can lead to loss of your funds, use at your own risk. Start with small amounts and protect your keys.

    • This Bot is provided as is, for learning purposes.
    • This bot is provided without any warranty of any kind, express or implied, including but not limited to the warranties of merchantability, fitness for a particular purpose, and non-infringement.
    • In no event shall the authors be liable for any claim, damages, or other liability.
    • Trading cryptocurrencies and tokens involves risk, and past performance is not indicative of future results.
    • The use of this bot is at your own risk, and we are not responsible for any losses incurred while using the bot.

    Setup

    To run the script you need to:

    • Create a new empty Solana wallet
    • Transfer some SOL to it.
    • Convert some SOL to WSOL (via Jupiter or Raydium).
    • Install dependencies by typing: npm install
    • Run the script by typing: npm run start in terminal
    • Updating .env, Use contents template inside the .env.example. (Check Configuration section bellow).

    Configuration

    Wallet

    • PRIVATE_KEY – Your wallet’s private key.

    Connection

    • RPC_ENDPOINT – HTTPS RPC endpoint for interacting with the Solana network.
    • RPC_WEBSOCKET_ENDPOINT – WebSocket RPC endpoint for real-time updates from the Solana network.
    • COMMITMENT_LEVEL– The commitment level of transactions (e.g., “finalized” for the highest level of security).

    Bot

    • LOG_LEVEL – Set logging level, e.g., info, debug, trace, etc.
    • ONE_TOKEN_AT_A_TIME – Set to true to process buying one token at a time.
    • COMPUTE_UNIT_LIMIT – Compute limit used to calculate fees.
    • COMPUTE_UNIT_PRICE – Compute price used to calculate fees.
    • TRANSACTION_EXECUTOR – default or jito
    • CUSTOM_FEE – If using warp or jito executors this value will be used for transaction fees instead of COMPUTE_UNIT_LIMIT and COMPUTE_UNIT_LIMIT
      • Minimum value is 0.0001 SOL, but recommend using 0.006 SOL or above
      • On top of this fee, minimal solana network fee will be applied
    • WAIT_FOR_RETRY_MS=800 – Wait in ms for each retrying (buy/sell)

    Buy

    • QUOTE_MINT – Which pools to snipe, USDC or WSOL.
    • QUOTE_AMOUNT – Amount used to buy each new token.
    • AUTO_BUY_DELAY – Delay in milliseconds before buying a token.
    • MAX_BUY_RETRIES – Maximum number of retries for buying a token.
    • BUY_SLIPPAGE – Slippage %

    Sell

    • AUTO_SELL – Set to true to enable automatic selling of tokens.
      • If you want to manually sell bought tokens, disable this option.
    • MAX_SELL_RETRIES – Maximum number of retries for selling a token.
    • AUTO_SELL_DELAY – Delay in milliseconds before auto-selling a token.
    • PRICE_CHECK_INTERVAL – Interval in milliseconds for checking the take profit and stop loss conditions.
      • Set to zero to disable take profit and stop loss.
    • PRICE_CHECK_DURATION – Time in milliseconds to wait for stop loss/take profit conditions.
      • If you don’t reach profit or loss bot will auto sell after this time.
      • Set to zero to disable take profit and stop loss.
    • TAKE_PROFIT – Percentage profit at which to take profit.
      • Take profit is calculated based on quote mint.
    • STOP_LOSS – Percentage loss at which to stop the loss.
      • Stop loss is calculated based on quote mint.
    • SELL_SLIPPAGE – Slippage %.

    Filters

    • CHECK_IF_MUTABLE – Set to true to buy tokens only if their metadata are not mutable.
    • CHECK_IF_SOCIALS – Set to true to buy tokens only if they have at least 1 social.
    • CHECK_IF_MINT_IS_RENOUNCED – Set to true to buy tokens only if their mint is renounced.
    • CHECK_IF_FREEZABLE – Set to true to buy tokens only if they are not freezable.
    • CHECK_IF_BURNED – Set to true to buy tokens only if their liquidity pool is burned.
    • MIN_LP_BURNED_PERCENT – Some tokens only send 1 token to burned, it’s better to calculate burned percent.
    • MIN_POOL_SIZE – Bot will buy only if the pool size is greater than or equal the specified amount.
      • Set 0 to disable.
    • MAX_POOL_SIZE – Bot will buy only if the pool size is less than or equal the specified amount.
      • Set 0 to disable.

    Some tips 👀

    • 🔨 The bot is a Tool, not a holy grail that will make you rich just by running it. If you don’t know what you are doing, you WILL lose money.
    • RPC / Network speed & good trading strategy is the key to success. You can speed up the bor but disabling AMMS not being used or too slow.
    • Not everything is so obvious. eg. a larger trade size can lead to smaller profits than a lower trade size.
    • If you frequently get 429 errors, try to reduce PRICE_CHECK_INTERVAL or FILTER_CHECK_INTERVAL.
    • If you can’t run the bot, it’s likely something wrong with the network, RPC, or config file

    Common issues

    If you have an error which is not listed here, please create a new issue in this repository.
    To collect more information on an issue, please change LOG_LEVEL to debug.

    • If you see following error in your log file:
      Error: 410 Gone: {"jsonrpc":"2.0","error":{"code": 410, "message":"The RPC call or parameters have been disabled."}, "id": "986f3599-b2b7-47c4-b951-074c19842bad" }
      it means your RPC node doesn’t support methods needed to execute script.

      • FIX: Change to use RPC node from some provider such as Helius or QuickNode…
    • If you see following error in your log file:
      Error: No SOL token account found in wallet:
      it means that wallet you provided doesn’t have USDC/WSOL token account.

      • To fix it: Go to dex (JUP for example) and swap some SOL to USDC/WSOL (tutorial)

    Visit original content creator repository
    https://github.com/meodien99/sol-sniper-bot

  • community-starter-kit

    welcome bot: A Probot App

    • Hey! Welcome to this repository
    • Its just a test
    • Feel free to lmk if theres any issues

    What it does

    • This does nothing
    • And even more nothing
    • …and more…
    • and yes… even more…

    Getting started

    1. Install the bot on the intended repositories. The plugin requires the following Permissions and Events:
    • Pull requests: Read & Write
    • Issues: Read & Write
    1. Create a .github/config.yml file to check for content of the comments:

    # Configuration for welcome - https://github.com/behaviorbot/welcome
    
    # Configuration for new-issue-welcome - https://github.com/behaviorbot/new-issue-welcome
    
    # Comment to be posted to on first time issues
    newIssueWelcomeComment: >
      Thanks for opening your first issue here! Be sure to follow the issue template!
    
    # Configuration for new-pr-welcome - https://github.com/behaviorbot/new-pr-welcome
    
    # Comment to be posted to on PRs from first time contributors in your repository
    newPRWelcomeComment: >
      Thanks for opening this pull request! Please check out our contributing guidelines.
    
    # Configuration for first-pr-merge - https://github.com/behaviorbot/first-pr-merge
    
    # Comment to be posted to on pull requests merged by a first time user
    firstPRMergeComment: >
      Congrats on merging your first pull request! We here at behaviorbot are proud of you!
    
    # It is recommended to include as many gifs and emojis as possible!
    

    You can opt out of having the bot comment on first time pull requests, pull request merges, or new issues by not filling in a value for each app’s respective field.

    For some inspiration about what kind of content to include in your .github/config files, check out Electron’s Configuration.

    Need help?

    If you need help using this app, we encourage you to:

    • Check out the Getting Started Guide in the docs folder of this repository
    • If you can’t find the answer there, open an issue in this repository and add the label question

    Project maintainers

    This project is maintained by Monalisa Octocat and friends. Use of this project under the MIT License.

    Visit original content creator repository
    https://github.com/theLadEli/community-starter-kit

  • ASOP_RAG

    Actuarial Standards of Practice (ASOP) Q&A machine using Retrieval Augmented Generation (RAG)

    1. Description

    This project aims to create a Retrieval-Augmented Generation (RAG) process for actuaries to ask questions on a set of Actuarial Standards of Practice (ASOP) documents. The RAG process utilizes the power of the Large Language Model (LLM) to provide answers to questions on ASOPs.

    However, RAG is not without challenges, i.e., hallucination and inaccuracy. The project example allows verifiability by providing the context an LLM used to arrive at those answers. This process enables actuaries to validate the LLM’s answers, empowering them to make informed decisions. By combining the capabilities of LLM with verifiability, this RAG process offers actuaries a robust tool to leverage LLM technology effectively and extract maximum value.

    The current example uses OpenAI’s GPT 3.5 turbo and open-source LLMs (e.g., Mistral 7B Instruct, SOLAR 10.7B Instruct). The open-source models can be used locally and can address potential data privacy or security concerns.

    Please see a Jupyter notebook (ASOP_RAG.ipynb) for details of the Python codes in the notebook folder. You can choose either Open AI or open-source LLM to use the RAG.
    An alternative notebook (ASOP_RAG_compare.ipynb) outputs the responses from both Open AI and an open-source LLM for comparison purposes.

    Here are the open-source models used:

    The RAG process used LangChain and Ollama frameworks.

    • LangChain is a framework for developing applications powered by LLMs.
    • Ollama is an effective way to get up and running with LLMs locally.

    See below for acknowledgments and references.

    2. Output

    2.1 Demo App

    Streamlit App
    Explore the potentials of RAG by visiting the Streamlit web app (https://asop-search.streamlit.app/) powered by GPT 3.5 turbo.

    2.2 Example Output

    Question

    User prompt: explain ASOP No. 14

    • Note: Asking this question to LLMs (such as ChatGPT 4) often leads to hallucination as they often explain the ASOP as if it is not repealed or refer to other ASOP documents.
    • Note: The RAG provides both the answer and context.

    Answer

    ASOP No. 14 was reviewed as part of a project to look at all cash flow testing standards of practice, and relevant portions were incorporated into the revisions of ASOP No. 7 and ASOP No. 22. The ASB voted to adopt the revised ASOP No. 7 and ASOP No. 22 and to repeal ASOP No. 14 in September 2001. The effective date of ASOP No. 7 was deferred to July 15, 2002, while concerns were reviewed regarding its applicability to property/casualty practice.

    Context

    Note: Providing context to the answer allows actuaries to review and validate.

    • Source 1: ../data/ASOP/asop007_128.pdf, page 5:
      virelated to cash flow testing. Finally, the ASB has adopted a new format for standards, and this standard has been rewritten to conform to that new format. In addition to ASOP No. 7, as part of the project to look at all cash flow testing standards of practice, ASOP No. 14 and ASOP No. 22 were al so reviewed. Relevant portions of ASOP No.
      14 were incorporated within the 2001 revisions of ASOP No. 7 and ASOP No. 22. At its September 2001 meeting, the ASB voted to adopt the revised ASOP No. 7 and ASOP No. 22 and to repeal ASOP No. 14. In April 2002, the ASB voted to defer the effective date of ASOP No. 7 to July 15, 2002 while it reviewed concerns raised by the Academy’s Casualty Practice Council regarding the standard’s applicability to property/casualty practice. At its June 2002 meeting, the ASB amended the scope to conform to generally accepted casualty actuarial practice. Please see appendix 3 for further information. Exposure Draft

    • Source 2: ../data/ASOP/asop004_173.pdf, page 31:
      are found in the current version of ASOP No. 4. The reviewers believe the reference to Precept 8 remains appropriate. The reviewers do not believe that the proposed change significantly improves the language included in the current version of ASOP No. 4, and made no change.

    • Source 3: … (all the context not shown in this illustration)

    3. Model

    3.1 Conceptual Flow

    RAG combines search and LLM generations.

    LLM completions are the results of model inference based on locked-in parameters. Any knowledge or information from LLM can be outdated unless augmented by external sources. RAG connects external documents, searches the document, and provides the relevant context to LLM. The external documents are transformed into a vector database during the initial setup stage for an effective search.

    For applications in practice, one should note that RAG is not perfect and can still lead to errors in searching or generating irrelevant or incorrect responses. As such, verifiability in RAG becomes crucial for actuarial use cases.

    RAG concept

    3.2 RAG Implementation Steps

    1. Decide whether to use OpenAI or local open-source models
    2. Select PDF documents (e.g., ASOP) to perform RAG
    3. Transform PDF into texts and divide them into chunks
    4. Convert the chunks into a vector database (Chroma DB) using embedding models (OpenAI, GPT4All)
    5. Retrieve and use LLM (GPT 3.5 Instruct, Solar 10.7B) to generate
    6. Output responses and context for a user to verify
    

    4. Author

    Dan Kim

    5. Date

    • Initially published on 2/12/2024
    • The contents may be updated from time to time

    6. License

    This project is licensed under the Apache License 2.0- see the LICENSE.md file for details.

    7. Acknowledgments and References

    Visit original content creator repository https://github.com/DanTCIM/ASOP_RAG
  • BinderFilter

    BinderFilter

    BinderFilter is a Linux kernel message firewall for Android. It is written as a kernel driver that implements reading, blocking, and modifying Android IPC messages. Our BinderFilter kernel driver hooks Android Binder’s kernel driver in /drivers/staging/android/binder.c.

    Android’s Binder IPC system completely mediates all inter-application messages, including requests by applications for private user data. We give users control and visibility over all such IPC messages, including dynamic permission blocking, with our open source BinderFilter project. This includes userland filtering, blocking, and logging of any IPC message in Android. Userland policy can be informed by the system’s context, i.e. environmental data such as GPS location and wifi network, which addresses the current lack of native Android support for context-based security policies.

    alt tag

    Parsing

    BinderFilter parses kernel IPC messages, which are often unencrpyted and assumed by applications to be secure – as demonstrated here. These messages include Intents sent to system services, and Intents to start new activities. An example IPC message from the GPS system service is shown below.

    {(0)@(29)(0)android.content.IIntentSender(0)(0)(0)(1)(0)(255)(255)(255)(255)(0)(0)(255)(255)(255)(255)(0)(0)(255)(255)(255)(255)(255)(255)(255)(255)(0)(0)(0)(0)(0)(0)(0)(0)(254)(255)(255)(255)(224)(4)(0)BNDL(3)(0)8(0)com.google.android.location.internal.EXTRA_LOCATION_LIST(0)(0)(11)(0)(1)(0)(4)(0)(25)(0)android.location.Location(0)(7)(0)network(0)(192)(191)(187)(145)T(1)(0)@(165)R(132)\(0)(177)(237)(254)(194)(60)(218)(69)(64)(121)(189)(234)(183)(101)(18)(82)(192)(0)(0)(0)(0)(0)(0)(0)(0)(0)(0)(0)(0)(0)(0)(1)(0)u(19)(...}
    

    The GPS coordinates of interest are re-cast below.

    *(double*)({177,237,254,194,60,218,69,64}) = 43.704979
    *(double*)({121,189,234,183,101,18,82,192}) = -72.287458
    

    Documentation

    See the wiki for documentation. For the writeup and slides, see ./presentations

    Usage

    See https://github.com/dxwu/BinderFilter/wiki/Usage

    Setup

    Because we hook an existing Linux driver, BinderFilter code requires a recompilation of the Linux source tree and flashing this new kernel onto an Android phone. We have tested and verified this method on a Google Nexus 7 (2013- flo). For development setup, see the related documentation. To install the pre-compiled kernel image:

    1. Root your Android phone

    2. Enable USB debugging

    3. Unlock bootloader

    4. Download fastboot and adb

    5. Connect your phone to the laptop with USB debugging enabled

    adb reboot bootloader
    fastboot flash boot ./resources/kernel-image.img
    
    1. Press start
    2. Phone will reboot, then install picky apk (adb install picky.apk) or the command line tools.

    Cross-compiling for Android

    This is a complex process. Please see “Compile linux kernel for android” in ./documentation/cross-compiling/cross_compiling.txt and https://github.com/dxwu/BinderFilter/wiki/Setup

    Picky

    Picky is the Android application that allows users to set firewall policy. See github.com/dxwu/Picky.

    Presentations

    This project has been presented at Summercon 2016 and Shmoocon 2017.

    Contributors

    This project started as a Senior Honors Thesis at Dartmouth College. Sergey Bratus advised and designed the project, and David Wu is the main contributer. Ionic Security has provided funding for testing phones and tablets.

    Visit original content creator repository https://github.com/dxwu/BinderFilter
  • java-langchains

    This repository aims to provide a java alternative to hwchase17/langchain. It was born from the need to create an enterprise QA application.

    Dependency

    java-langchains requires Java 8 or higher

    To group this repository with other related repositories in the future we lately transferred this repository to the freshly created organization cupybara. Therefore we changed the package names from com.github.hakenadu to io.github.cupybara and also changed the groupId. The latest artifact is therefore available by using the following dependency:

    <dependency>
        <groupId>io.github.cupybara</groupId>
        <artifactId>java-langchains</artifactId>
        <version>0.6.3</version>
    </dependency>

    deprecated older dependency

    Packages up to version 0.5.0 are available using the groupId com.github.hakenadu. These artifacts are not updates anymore so we don’t suggest to use them. Please switch to io.github.cupybara.

    old dependency
    <dependency>
        <groupId>com.github.hakenadu</groupId>
        <artifactId>java-langchains</artifactId>
        <version>0.5.0</version>
    </dependency>

    Chains

    Modular components implement the Chain interface. This provides an easy way to modularize the application and enables us to reuse them for various use cases.

    This section describes the usage of all chains that are currently available.

    Base

    Logging

    The LoggingChain can be used to log the previous chain’s output. Take a look at the RetrievalQaTest to see some example usages (logging chains indented for improved readability):

    final Chain<String, AnswerWithSources> qaChain = retrievalChain
    		.chain(summarizeDocumentsChain)
    			.chain(new ApplyToStreamInputChain<>(new LoggingChain<>(LoggingChain.defaultLogPrefix("SUMMARIZED_DOCUMENT"))))
    		.chain(combineDocumentsChain)
    			.chain(new LoggingChain<>(LoggingChain.defaultLogPrefix("COMBINED_DOCUMENT")))
    		.chain(openAiChatChain)
    			.chain(new LoggingChain<>(LoggingChain.defaultLogPrefix("LLM_RESULT")))
    		.chain(mapAnswerWithSourcesChain);

    The summarizeDocumentsChain in this example provides a Stream as an output. To log each item of the Stream the LoggingChain can be wrapped in an ApplyToStreamInputChain.

    This example provides the following log output running the RetrievalQaTest:

    ========================================================================================================================================================
    SUMMARIZED_DOCUMENT
    ========================================================================================================================================================
    {source=book-of-john-1.pdf, question=who is john doe?, content=John Doe is a highly skilled and experienced software engineer with a passion for problem-solving and creating innovative solutions. He has been working in the technology industry for over 15 years and has gained a reputation for his exceptional programming abilities and attention to detail.}
    
    ========================================================================================================================================================
    SUMMARIZED_DOCUMENT
    ========================================================================================================================================================
    {source=book-of-john-3.pdf, question=who is john doe?, content=John Doe is described as someone with a diverse range of hobbies and interests. Some of his notable hobbies include music production, culinary adventures, photography and travel, fitness and outdoor activities, and being a book club enthusiast. He is also involved in volunteering and community service, language learning, gardening, DIY projects, and astronomy.}
    
    ========================================================================================================================================================
    COMBINED_DOCUMENT
    ========================================================================================================================================================
    {question=who is john doe?, content=Content: John Doe is described as someone with a diverse range of hobbies and interests. Some of his notable hobbies include music production, culinary adventures, photography and travel, fitness and outdoor activities, and being a book club enthusiast. He is also involved in volunteering and community service, language learning, gardening, DIY projects, and astronomy.
    Source: book-of-john-3.pdf
    
    Content: John Doe is a highly skilled and experienced software engineer with a passion for problem-solving and creating innovative solutions. He has been working in the technology industry for over 15 years and has gained a reputation for his exceptional programming abilities and attention to detail.
    Source: book-of-john-1.pdf}
    
    ========================================================================================================================================================
    LLM_RESULT
    ========================================================================================================================================================
    John Doe is described as someone with a diverse range of hobbies and interests, including music production, culinary adventures, photography, travel, fitness, outdoor activities, being a book club enthusiast, volunteering, community service, language learning, gardening, DIY projects, and astronomy. Additionally, John Doe is a highly skilled and experienced software engineer with a passion for problem-solving and creating innovative solutions. He has been working in the technology industry for over 15 years and is known for his exceptional programming abilities and attention to detail.
    SOURCES: book-of-john-3.pdf, book-of-john-1.pdf
    

    Data

    Reader

    Read Documents from In Memory PDF

    See ReadDocumentsFromInMemoryPdfChainTest

    Read the in memory pdf into a single document

    InMemoryPdf inMemoryPdf = new InMemoryPdf(
    	IOUtils.toByteArray(ReadDocumentsFromInMemoryPdfChainTest.class.getResourceAsStream("/pdf/qa/book-of-john-3.pdf")),
    	"my-in-memory.pdf");
    	
    Stream<Map<String, String>> readDocuments = new ReadDocumentsFromInMemoryPdfChain().run(inMemoryPdf)
    	
    // the readDocuments contains a (pdfContent, "my-in-memory.pdf") pair

    Read documents for each page of the in memory pdf

    InMemoryPdf inMemoryPdf = new InMemoryPdf(
    	IOUtils.toByteArray(ReadDocumentsFromInMemoryPdfChainTest.class.getResourceAsStream("/pdf/qa/book-of-john-3.pdf")),
    	"my-in-memory.pdf");
    	
    Stream<Map<String, String>> readDocuments = new ReadDocumentsFromInMemoryPdfChain(PdfReadMode.PAGES).run(inMemoryPdf)
    	
    // the readDocuments contains (content, source) pairs for all read pdf pages (source is "my-in-memory.pdf" + the pdf page number)
    Read Documents from PDF

    See ReadDocumentsFromPdfChainTest

    Read each pdf in the given directory into a single document each

    Stream<Map<String, String>> readDocuments = new ReadDocumentsFromPdfChain()
    	.run(Paths.get("path/to/my/pdf/folder"))
    	
    // the readDocuments contains (content, source) pairs for all read pdfs (source is the pdf filename)

    Read each page of each pdf in the given directory into a single document each

    Stream<Map<String, String>> readDocuments = new ReadDocumentsFromPdfChain(PdfReadMode.PAGES)
    	.run(Paths.get("path/to/my/pdf/folder"))
    	
    // the readDocuments contains (content, source) pairs for all read pdf pages (source is the pdf filename + the pdf page number)

    Retrieval

    Retrieve Documents from Elasticsearch Index

    See ElasticsearchRetrievalChainIT

    RestClientBuilder restClientBuilder = RestClient.builder(new HttpHost("localhost", 9200));
    
    Chain<Path, Void> createElasticsearchIndexChain = new ReadDocumentsFromPdfChain()
    	.chain(new WriteDocumentsToElasticsearchIndexChain("my-index", restClientBuilder));
    
    Path pdfDirectoryPath = Paths.get(ElasticsearchRetrievalChainTest.class.getResource("/pdf/qa").toURI());
    
    // create and fill elasticsearch index with read pdfs (source, content)-pairs
    createElasticsearchIndexChain.run(pdfDirectoryPath);
    
    // retrieve documents relevant to a specific question
    try (RestClient restClient = restClientBuilder.build();
    		ElasticsearchRetrievalChain retrievalChain = new ElasticsearchRetrievalChain("my-index", restClient, 1)) {
    
    	// retrieve the most relevant documents for the passed question
    	Stream<Map<String, String>> retrievedDocuments = retrievalChain.run("who is john doe?").collect(Collectors.toList());
    
    	// ...
    }
    Retrieve Documents from Lucene Directory

    See LuceneRetrievalChainTest

    // create lucene index
    Directory directory = new MMapDirectory(Files.createTempDirectory("myTempDir"));
    
    // fill lucene index
    try (IndexWriter indexWriter = new IndexWriter(directory, new IndexWriterConfig(new StandardAnalyzer()))) {
    	List<String> documents = Arrays.asList("My first document", "My second document", "My third document");
    
    	for (String content : documents) {
    		Document doc = new Document();
    		doc.add(new TextField(PromptConstants.CONTENT, content, Field.Store.YES));
    		doc.add(new StringField(PromptConstants.SOURCE, String.valueOf(documents.indexOf(content) + 1), Field.Store.YES));
    		indexWriter.addDocument(doc);
    	}
    
    	indexWriter.commit();
    }
    
    // create retrieval chain
    RetrievalChain retrievalChain = new LuceneRetrievalChain(directory, 2 /* max count of retrieved documents */);
    
    // retrieve the most relevant documents for the passed question
    Stream<Map<String, String>> retrievedDocuments = retrievalChain.run("my question?");
    Retrieve Documents from RDBMS

    See JdbcRetrievalChainIT

    Supplier<Connection> connectionSupplier = () -> {
    	try {
    		return DriverManager.getConnection(connectionString, username, password);
    	} catch (SQLException e) {
    		throw new IllegalStateException("error creating database connection", e);
    	}
    };
    
    RetrievalChain retrievalChain = new JdbcRetrievalChain(connectionSupplier, 2 /* max count of retrieved documents */);
    
    Stream<Map<String, String>> retrievedDocuments = retrievalChain.run("my question?");

    Writer

    Write Documents to Elasticsearch Index
    RestClientBuilder restClientBuilder = RestClient.builder(new HttpHost("localhost", 9200));
    
    // this chain reads documents from a folder of pdfs and writes them to an elasticsearch index
    Chain<Path, Void> fillElasticsearchIndexChain = new ReadDocumentsFromPdfChain()
      .chain(new WriteDocumentsToElasticsearchIndexChain("my-index", restClientBuilder));
    
    Path pdfDirectoryPath = Paths.get(getClass().getResource("/pdf/qa").toURI());
    
    fillElasticsearchIndexChain.run(pdfDirectoryPath);
    Write Documents to Lucene Directory
    Path tempIndexPath = Files.createTempDirectory("lucene")
    
    // this chain reads documents from a folder of pdfs and writes them to an index directory
    Chain<Path, Directory> createLuceneIndexChain = new ReadDocumentsFromPdfChain()
    	.chain(new WriteDocumentsToLuceneDirectoryChain(tempIndexPath));
    
    Path pdfDirectoryPath = Paths.get(getClass().getResource("/pdf/qa").toURI());
    
    Directory directory = createLuceneIndexChain.run(pdfDirectoryPath);

    LLM

    Azure

    Azure Chat

    See AzureOpenAiChatCompletionsChainIT

    AzureOpenAiChatCompletionsChain chain = new AzureOpenAiChatCompletionsChain(
    	"my-azure-resource-name",
    	"gpt-35-turbo", // deployment name
    	"2023-05-15", // api version
    	"Hello, this is ${name}", 
    	new OpenAiChatCompletionsParameters().temperature(0D), // also allows to set more parameters
    	System.getenv("OPENAI_API_KEY"),
    	"You are a helpful assistant who answers questions to ${name}" // optional systemTemplate 
    );
    
    String result = chain.run(Collections.singletonMap("name", "Manuel")); 
    // the above outputs something like: "Hello Manuel, how are you"
    Azure Completions
    AzureOpenAiCompletionsChain chain = new AzureOpenAiCompletionsChain(
    	"my-azure-resource-name",
    	"text-davinci-003", // deployment name
    	"2023-05-15", // api version
    	"Hello, this is ${name}", 
    	new OpenAiCompletionsParameters().temperature(0D), // also allows to set more parameters
    	System.getenv("OPENAI_API_KEY"),
    	"You are a helpful assistant who answers questions to ${name}" // optional systemTemplate 
    );
    
    String result = chain.run(Collections.singletonMap("name", "Manuel"));
    // the above outputs something like: "Hello Manuel, how are you"

    OpenAI

    OpenAI Chat

    See OpenAiChatCompletionsChainIT

    OpenAiChatCompletionsChain chain = new OpenAiChatCompletionsChain(
    	"Hello, this is ${name}", 
    	new OpenAiChatCompletionsParameters().model("gpt-3.5-turbo").temperature(0D), // also allows to set more parameters
    	System.getenv("OPENAI_API_KEY"),
    	"You are a helpful assistant who answers questions to ${name}" // optional systemTemplate 
    );
    
    String result = chain.run(Collections.singletonMap("name", "Manuel"));
    // the above outputs something like: "Hello Manuel, how are you"

    OpenAI Completions

    OpenAiCompletionsChain chain = new OpenAiCompletionsChain(
    	"Hello, this is ${name}", 
    	new OpenAiCompletionsParameters().model("text-davinci-003").temperature(0D), // also allows to set more parameters
    	System.getenv("OPENAI_API_KEY"),
    	"You are a helpful assistant who answers questions to ${name}" // optional systemTemplate 
    );
    
    String result = chain.run(Collections.singletonMap("name", "Manuel"));
    // the above outputs something like: "Hello Manuel, how are you"

    QA

    Modify Documents

    The ModifyDocumentsContentChain can be used for document summarization (for example).

    // create the llm chain which is used for summarization
    LargeLanguageModelChain llmChain = new OpenAiChatCompletionsChain(
    		PromptTemplates.QA_SUMMARIZE, 
    		new OpenAiChatCompletionsParameters().temperature(0D).model("gpt-3.5-turbo"),
    		System.getenv("OPENAI_API_KEY"));
    
    // create the ModifyDocumentsContentChain which is used to apply the llm chain to each passed document
    ModifyDocumentsContentChain summarizeDocumentsChain = new ModifyDocumentsContentChain(llmChain);
    
    // create some example documents
    Map<String, String> myFirstDocument = new HashMap<String, String>();
    myFirstDocument.put(PromptConstants.CONTENT, "this is my first document content");
    myFirstDocument.put(PromptConstants.SOURCE, "this is my first document source");
    // the default summarize prompt PromptTemplates.QA_SUMMARIZE also expects the question used for retrieval in the document
    myFirstDocument.put(PromptConstants.QUESTION, "who is John Doe?");
    
    Map<String, String> mySecondDocument = new HashMap<String, String>();
    mySecondDocument.put(PromptConstants.CONTENT, "this is my second document content");
    mySecondDocument.put(PromptConstants.SOURCE, "this is my second document source");
    mySecondDocument.put(PromptConstants.QUESTION, "how old is John Doe?"); // see comment above
    
    // input for the summarize chain is a stream of documents
    Stream<Map<String, String>> documents = Stream.of(myFirstDocument, mySecondDocument);
    
    // output contains the passed documents with summarized content-Value
    Stream<Map<String, String>> summarizedDocuments = summarizeDocumentsChain.run(documents);

    Combine Documents

    CombineDocumentsChain combineDocumentsChain = new CombineDocumentsChain();
    
    Map<String, String> myFirstDocument = new HashMap<String, String>();
    myFirstDocument.put(PromptConstants.CONTENT, "this is my first document content");
    myFirstDocument.put(PromptConstants.SOURCE, "this is my first document source");
    
    Map<String, String> mySecondDocument = new HashMap<String, String>();
    mySecondDocument.put(PromptConstants.CONTENT, "this is my second document content");
    mySecondDocument.put(PromptConstants.SOURCE, "this is my second document source");
    
    Stream<Map<String, String>> documents = Stream.of(myFirstDocument, mySecondDocument);
    
    Map<String, String> combinedDocument = combineDocumentsChain.run(documents);
    /* 
     * Content: this is my first document content
     * Source: this is my first document source
     *
     * Content: this is my second document content
     * Source: this is my second document source
     * 
     * (stored with key "content" inside the map)
     */

    Map LLM results to answers with sources

    MapAnswerWithSourcesChain mapAnswerWithSourcesChain = new MapAnswerWithSourcesChain();
    
    AnswerWithSources answerWithSources = mapAnswerWithSourcesChain.run("The answer is bla bla bla.\nSOURCES: page 1 book xy, page 2 book ab");
    
    System.out.println(answerWithSources.getAnswer());  // The answer is bla bla bla.
    System.out.println(answerWithSources.getSources()); // [page 1 book xy, page 2 book ab]

    Split Documents

    See SplitDocumentsChainTest

    // 1. Create Documents
    
    List<Map<String, String>> documents = new LinkedList<>();
    
    Map<String, String> firstDocument = new LinkedHashMap<>();
    firstDocument.put(PromptConstants.SOURCE, "book of john");
    firstDocument.put(PromptConstants.CONTENT, "This is a short text. This is another short text.");
    documents.add(firstDocument);
    
    Map<String, String> secondDocument = new LinkedHashMap<>();
    secondDocument.put(PromptConstants.SOURCE, "book of jane");
    secondDocument.put(PromptConstants.CONTENT, "This is a short text.");
    documents.add(secondDocument);
    
    // 2. Split Documents
    
    /*
     * We create a TextSplitter that splits a text into partitions using a JTokkit
     * Encoding. We use the cl100k_base encoding (which btw is the default for
     * gpt-3.5-turbo)
     */
    TextSplitter textSplitter = new JtokkitTextSplitter(
    		Encodings.newDefaultEncodingRegistry().getEncoding(EncodingType.CL100K_BASE), 10);
    
    /*
     * we now instantiate the SplitDocumentsChain which will split our documents
     * using the above created TextSplitter on the "content" field.
     */
    SplitDocumentsChain splitDocumentsChain = new SplitDocumentsChain(textSplitter);
    
    List<Map<String, String>> splitDocuments = splitDocumentsChain.run(documents.stream())
    		.collect(Collectors.toList());
    
    // splitDocuments: [
    //   {content=This is a short text. , source=book of john},
    //   {content=This is another short text., source=book of john},
    //   {content=This is a short text., source=book of jane}
    // ]

    Usage behind a corporate proxy

    If a chain needs to access to an external service, there will be a constructor parameter for passing the http client. The WebClient is used for the following chains:

    There exists plenty of public documentation on how to configure a http proxy for those cases. One example is this one from Baeldung.

    For accessing an Elasticsearch cluster the Elasticsearch Low Level Client is used. The official documentation shows how to use a proxy in this case.

    Use Cases

    Multiple chains can be chained together to create more powerful chains for complex use cases.

    Document Comparison

    The following unit test shows how the existing chains may be used to compare 2 or more documents. I guess more abstraction would be useful. I will target that in one of the next releases and then also include example code in this README.

    The following diagram shows how the implementation for this usecase works:

    Retrieval Question-Answering Chain

    The following unit test provides a comprehensive solution for an information retrieval and summarization task, with the aim to provide concise, informative and relevant answers from a large set of documents. It combines multiple processes into a Question-Answering (QA) chain, each responsible for a specific task.

    /*
     * take a look at src/test/resources/pdf of this repository
     * the pdf directory contains three documents about a fictional person named john doe
     * which we want to query using our retrieval based qa with sources chain
     */
    Path pdfDirectoryPath = Paths.get(RetrievalQaTest.class.getResource("/pdf/qa").toURI());
    
    /*
     * We are creating and running an initializing chain which reads document from our pdf folder
     * and writes them to a lucene index directory
     */
    Directory directory =  new ReadDocumentsFromPdfChain().chain(new WriteDocumentsToLuceneDirectoryChain()).run(pdfDirectoryPath);
    
    // we got multiple OpenAI LLM Chains and define our parameters at first
    OpenAiChatCompletionsParameters openAiChatParameters = new OpenAiChatCompletionsParameters()
    		.temperature(0D)
    		.model("gpt-3.5-turbo");
    
    /*
     * Chain 1: The retrievalChain is used to retrieve relevant documents from an
     * index by using bm25 similarity
     */
    try (LuceneRetrievalChain retrievalChain = new LuceneRetrievalChain(directory /* implies a filled lucene directory */, 2)) {
    
    	/*
    	 * Chain 2: The summarizeDocumentsChain is used to summarize documents to only
    	 * contain the most relevant information. This is achieved using an OpenAI LLM
    	 * (gpt-3.5-turbo in this case)
    	 */
    	ModifyDocumentsContentChain summarizeDocumentsChain = new ModifyDocumentsContentChain(new OpenAiChatCompletionsChain(
    			PromptTemplates.QA_SUMMARIZE, openAiChatParameters, System.getenv("OPENAI_API_KEY")));
    
    	/*
    	 * Chain 3: The combineDocumentsChain is used to combine the retrieved documents
    	 * in a single prompt
    	 */
    	CombineDocumentsChain combineDocumentsChain = new CombineDocumentsChain();
    
    	/*
    	 * Chain 4: The openAiChatChain is used to process the combined prompt using an
    	 * OpenAI LLM (gpt-3.5-turbo in this case)
    	 */
    	OpenAiChatCompletionsChain openAiChatChain = new OpenAiChatCompletionsChain(PromptTemplates.QA_COMBINE,
    			openAiChatParameters, System.getenv("OPENAI_API_KEY"));
    
    	/*
    	 * Chain 5: The mapAnswerWithSourcesChain is used to map the llm string output
    	 * to a complex object using a regular expression which splits the sources and
    	 * the answer.
    	 */
    	MapAnswerWithSourcesChain mapAnswerWithSourcesChain = new MapAnswerWithSourcesChain();
    
    	// we combine all chain links into a self contained QA chain
    	Chain<String, AnswerWithSources> qaChain = retrievalChain
    		.chain(summarizeDocumentsChain)
    		.chain(combineDocumentsChain)
    		.chain(openAiChatChain)
    		.chain(mapAnswerWithSourcesChain);
    
    	// the QA chain can now be called with a question and delivers an answer
    	AnswerWithSources answerWithSources = qaChain.run("who is john doe?");
    	
    	/*
    	 * answerWithSources.getAnwswer() provides the answer to the question based on the retrieved documents
    	 * answerWithSources.getSources() provides a list of source strings for the retrieved documents
    	 */
    }

    The QA chain performs the following tasks:

    1. Document Retrieval: This step is responsible for retrieving the most relevant documents related to a given query from a large collection. It uses an index-based search algorithm to find documents containing information related to the input query. This functionality can be facilitated by any RetrievalChain implementation. LuceneRetrievalChain, which utilizes the BM25 similarity metric, is just an example used in the test case.

    2. Document Summarization: Once relevant documents are retrieved, they need to be summarized to extract the most essential information. The SummarizeDocumentsChain uses an instance of LargeLanguageModelChain for this task. In the provided example, OpenAI’s GPT-3.5-turbo model via OpenAiChatCompletionsChain is used to reduce the information to its most relevant content.

    3. Document Combination: The CombineDocumentsChain combines the summarized documents into a single prompt. This forms the input to the next stage of the process.

    4. Answer Generation: The OpenAiChatCompletionsChain uses the combined prompt to generate a response. Any instance of LargeLanguageModelChain can be used for this step. In the given example, OpenAI’s GPT-3.5-turbo model is utilized.

    5. Mapping and Answer Extraction: Finally, the MapAnswerWithSourcesChain maps the string output to a complex object using a regular expression, which splits the answer from the sources of information. This provides a structured output that includes both the answer to the query and the sources from which the answer was derived.

    In conclusion, the QA chain represents a comprehensive solution for document-based question-answering tasks, providing not only the most relevant answer but also citing the sources from which the information was retrieved. This chain is particularly useful in contexts where understanding the origin of information is as crucial as the answer itself.

    Visit original content creator repository https://github.com/cupybara/java-langchains
  • yudian-ai-508

    YUDIAN AI-508 Temperature Controller Driver

    The LabVIEW driver for YUDIAN Artificial Intelligence Temperature Controller, used by many automatic controlled furnaces (e.g. furnaces made by MTI Corp.) You may use this driver to easily integrate your smart furnaces into your process control software and fabrication workflow.

    Contribution

    I developed this driver during my spare time when I was still working on electronics packaging and semiconductor fabrication. The driver was originally shared on NI forum but not very accessible.

    You are welcome to make contributions to this repo by creating an issue or pull-request. I will review them every month and maintain this repo with my best efforts.

    Usage

    This is a third-party LabVIEW driver for RS485 communication bus. MIT license.

    VISA API

    If you have a VISA time-out problem. This is how to debug it:

    • First use its official software and see if it works, if so, it indicates the software problem, otherwise, you have the hardware problem.
      You also need check with your controller, it has to allow the remote control mode or it supports remote control.

    • If you are using the right cable and the official software comes with the controller does work, you need use a serial port communication monitor software to monitor all the communication on the serial port and carefully compare it to the communication log data with official software. I use this tool

    • It is free while I was debugging this. Once you find the difference between this driver and the official one, revise the code according to the official protocol and it shall work. You may contribute your update this repo and it could benefit everyone.

    • It might because that YUDIAN recently upgrade the firmware of AI-508 and the existing driver no longer works. If so, you may debug this version and update to the new version. And you are welcome to upload your revision to share with other engineers.

    RS485 Bus

    I recommend to use a generic USB/RS485 converter. This driver only supports RS485 protocol. This is NOT RS232. if you use most common RS232, it won’t work.

    To configure the RS485, you need setup it according to the user manual of your converter and your PC. Then, if you have multiple devices on the RS485 bus, make sure that you choose the correct address, e.g. You need to use the corresponding address number in every sub vi.

    Programming

    You may setup the number of steps/segments in your controller program. You also need to set the temperatures and time for each segment. You can also download current program from the controller to double check it.

    While your program is running, you may use a while loop (or a thread) to get the real-time temperature reading periodically and integrate it with any other control logic.

    All those sub vi, you can find in the sub folder and they have been tested. You may stop the program using stop vi. In all, go thru the source code first, you will find the driver is straightforward and easy to understand and use.

    Visit original content creator repository
    https://github.com/yangfh2004/yudian-ai-508