import java.util.regex.Matcher;
import java.util.regex.Pattern;
public class Example {
public static void main(String[] args) {
final String regex = "\\/\\*\\*?\\s*([\\W\\w]*?)\\s*\\*\\/|\\/\\/\\s*(.*)$";
final String string = "/**\n"
+ " * The Crypto Info Bot\n"
+ " *\n"
+ " * @author Denis Efremov <efremov.a.denis@gmail.com>\n"
+ " */\n"
+ "require('dotenv').load()\n\n"
+ "const axios = require('axios')\n"
+ "const winston = require('winston')\n"
+ "const { inspect } = require('util')\n"
+ "const Telegraf = require('telegraf')\n\n"
+ "const { session } = Telegraf\n"
+ "const {\n"
+ " API_URL,\n"
+ " BOT_TOKEN,\n"
+ " BOT_USERNAME,\n"
+ " PAGE_SIZE,\n"
+ " FIXED_LENGTH,\n"
+ "} = process.env\n\n"
+ "/**\n"
+ " * Debug helper\n"
+ " *\n"
+ " * @param {Mixed} data The data\n"
+ " * @return {Mixed}\n"
+ " */\n"
+ "const debug = (data) => console.log(inspect(data, {\n"
+ " showHidden: true,\n"
+ " colors: true,\n"
+ " depth: 10,\n"
+ "}))\n\n"
+ "const logger = winston.createLogger({\n"
+ " level: 'info',\n"
+ " format: winston.format.json(),\n"
+ " transports: [\n"
+ " new winston.transports.File({ filename: 'log/error.log', level: 'error' }),\n"
+ " new winston.transports.File({ filename: 'log/combined.log' }),\n"
+ " ],\n"
+ "})\n\n"
+ "const formattedTime = (date) => date.toTimeString()\n"
+ "const formattedDate = (date) => date.toDateString()\n"
+ "const formattedDateTime = (date) => \\`${formattedDate(date)} ${formattedTime(date)}\\`\n\n"
+ "/**\n"
+ " * Create a new bot instance\n"
+ " *\n"
+ " * @type {Telegraf}\n"
+ " */\n"
+ "const bot = new Telegraf(BOT_TOKEN, { username: BOT_USERNAME })\n\n"
+ "bot.use(session())\n\n"
+ "/**\n"
+ " * Render pagination buttons\n"
+ " *\n"
+ " * @param {String} ns The namespace\n"
+ " * @param {Number} page The page\n"
+ " * @param {Number} total The total\n"
+ " * @return {Object} Message parameters\n"
+ " */\n"
+ "const pagination = (namespace, page, total) => ({\n"
+ " reply_markup: {\n"
+ " inline_keyboard: [[\n"
+ " page !== 0\n"
+ " ? { text: `< Prev ${PAGE_SIZE}`, callback_data: `/${namespace}/prev` }\n"
+ " : { text: '----------', callback_data: '/noop' },\n"
+ " {\n"
+ " text: `${page * PAGE_SIZE} - ${(page + 1) * PAGE_SIZE} (${total})`,\n"
+ " callback_data: '/noop',\n"
+ " },\n"
+ " page !== (total / PAGE_SIZE) - 1\n"
+ " ? { text: `Next ${PAGE_SIZE} >`, callback_data: `/${namespace}/next` }\n"
+ " : { text: '----------', callback_data: '/noop' },\n"
+ " ]],\n"
+ " },\n"
+ "})\n\n"
+ "/**\n"
+ " * Gets the rates.\n"
+ " *\n"
+ " * @param {Number} start The start\n"
+ " * @param {Number} limit The limit\n"
+ " * @return {Promise} The rates\n"
+ " */\n"
+ "const getRates = (start, limit) => {\n"
+ " let url = `${API_URL}?convert=RUB`\n\n"
+ " if (limit) {\n"
+ " url += `&limit=${limit}`\n"
+ " }\n\n"
+ " if (start) {\n"
+ " url += `&start=${start}`\n"
+ " }\n\n"
+ " return axios.get(url)\n"
+ "}\n\n"
+ "/**\n"
+ " * Gets the rate.\n"
+ " *\n"
+ " * @param {String} asset The asset\n"
+ " * @return {Promise} The rate\n"
+ " */\n"
+ "const getRate = (asset) => axios.get(`${API_URL}${asset}/?convert=RUB`)\n\n"
+ "/**\n"
+ " * A currency message template\n"
+ " *\n"
+ " * @param {Object} rate The rate object\n"
+ " * @param {String} rate.name The name\n"
+ " * @param {String} rate.symbol The symbol\n"
+ " * @param {Number} rate.price_usd The price usd\n"
+ " * @param {Number} rate.price_rub The price rub\n"
+ " * @param {Number} rate.percent_change_1h:hour The percent change 1 h hour\n"
+ " * @param {Number} rate.percent_change_24h:day The percent change 24 h day\n"
+ " * @param {Number} rate.percent_change_7d:week The percent change 7 d week\n"
+ " * @return {String}\n"
+ " */\n"
+ "const templateMd = ({\n"
+ " name, symbol, price_usd, price_rub,\n"
+ " percent_change_1h: hour,\n"
+ " percent_change_24h: day,\n"
+ " percent_change_7d: week,\n"
+ "}) => `${name} *(${symbol})* \\`!${symbol.toLowerCase()}\\`\n"
+ "\\`\\`\\`\n"
+ "==================\n"
+ "$ ${price_usd}\n"
+ "₽ ${price_rub}\n"
+ "==================\n"
+ "${hour > 0 ? '+' : ''}${parseFloat(hour).toFixed(FIXED_LENGTH)}% / 1h\n"
+ "${day > 0 ? '+' : ''}${parseFloat(day).toFixed(FIXED_LENGTH)}% / 24h\n"
+ "${week > 0 ? '+' : ''}${parseFloat(week).toFixed(FIXED_LENGTH)}% / 7d\n"
+ "\\`\\`\\``\n\n"
+ "/**\n"
+ " * A currency message small template\n"
+ " *\n"
+ " * @param {Object} rate The rate object\n"
+ " * @param {String} rate.name The name\n"
+ " * @param {String} rate.symbol The symbol\n"
+ " * @param {Number} rate.price_usd The price usd\n"
+ " * @param {Number} rate.price_rub The price rub\n"
+ " * @return {String}\n"
+ " */\n"
+ "const smallTemplateMd = ({ name, symbol, price_usd, price_rub }) => `\n"
+ "${name} *(${symbol})* \\`!${symbol.toLowerCase()}\\`\n"
+ "\\`\\`\\`\n"
+ "$ ${price_usd} | ₽ ${price_rub}\n"
+ "\\`\\`\\``\n\n"
+ "/**\n"
+ " * Map command listaners\n"
+ " *\n"
+ " * @param {Object[]} rates The rates\n"
+ " * @return {Promise}\n"
+ " */\n"
+ "const mapCommands = async (/*rates*/) => rates.reduce((acc, rate) => {\n"
+ " const command = rate.symbol.toLowerCase()\n\n"
+ " bot.hears(`!${command}`, async (ctx) => {\n"
+ " let intervalId\n"
+ " let response = await getRate(ctx.index[command]).catch((error) => {\n"
+ " debug(error)\n"
+ " clearInterval(intervalId)\n"
+ " })\n"
+ " let text = templateMd(response.data[0])\n"
+ " let message = await ctx.replyWithMarkdown(\n"
+ " `${text}\n"
+ "Updated: ${formattedTime(new Date()).slice(0, 8)}`\n"
+ " ).catch((error) => {\n"
+ " debug(error)\n"
+ " clearInterval(intervalId)\n"
+ " })\n\n"
+ " message.text = text\n\n"
+ " intervalId = setInterval(async () => {\n"
+ " response = await getRate(ctx.index[command]).catch((error) => {\n"
+ " debug(error)\n"
+ " clearInterval(intervalId)\n"
+ " })\n\n"
+ " text = templateMd(response.data[0])\n\n"
+ " if (text === message.text) {\n"
+ " return\n"
+ " }\n\n"
+ " message = await ctx.tg.editMessageText(\n"
+ " ctx.chat.id,\n"
+ " message.message_id,\n"
+ " undefined,\n"
+ " `${text}\n"
+ "Updated: ${formattedTime(new Date()).slice(0, 8)}`,\n"
+ " { parse_mode: 'Markdown' }\n"
+ " ).catch((error) => {\n"
+ " debug(error)\n"
+ " clearInterval(intervalId)\n"
+ " })\n"
+ " message.text = text\n"
+ " }, 5000)\n"
+ " })\n\n"
+ " acc[command] = rate.id\n\n"
+ " return acc\n"
+ "}, {})\n\n"
+ "bot.use((ctx, next) => {\n"
+ " logger.log({ level: 'info', message: ctx.message })\n"
+ " debug(ctx.message)\n"
+ " next()\n"
+ "})\n\n"
+ "/**\n"
+ " * The rates command\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "bot.hears('!rates', async (ctx) => {\n"
+ " ctx.session.ratesPage = ctx.session.ratesPage || 0\n\n"
+ " const { data } = await getRates(\n"
+ " ctx.session.ratesPage * PAGE_SIZE,\n"
+ " (ctx.session.ratesPage * PAGE_SIZE) + PAGE_SIZE\n"
+ " )\n\n"
+ " await ctx.replyWithMarkdown(\n"
+ " data.map(smallTemplateMd).join(''),\n"
+ " pagination('rates', ctx.session.ratesPage, Object.keys(ctx.index).length),\n"
+ " ).catch(debug)\n"
+ "})\n\n"
+ "/**\n"
+ " * The time command\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "bot.hears('!time', async (ctx) => {\n"
+ " const message = await ctx.replyWithMarkdown(formattedDateTime(new Date()))\n"
+ " .catch(debug)\n\n"
+ " const intervalId = setInterval(async () => {\n"
+ " await ctx.tg.editMessageText(\n"
+ " ctx.chat.id,\n"
+ " message.message_id,\n"
+ " undefined,\n"
+ " formattedDateTime(new Date())\n"
+ " ).catch((error) => {\n"
+ " debug(error)\n"
+ " clearInterval(intervalId)\n"
+ " })\n"
+ " }, 3000)\n"
+ "})\n\n"
+ "/**\n"
+ " * The currencies list command\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "bot.hears('!list', async (ctx) => {\n"
+ " const text = Object.keys(ctx.index)\n"
+ " .map((key) => `\n"
+ "${ctx.index[key]} \\`!${key}\\``)\n"
+ " .join('')\n\n"
+ " await ctx.replyWithMarkdown(text).catch(debug)\n"
+ "})\n\n"
+ "/**\n"
+ " * Change page action\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "bot.action(/^/rates/(w+)$/, async (ctx) => {\n"
+ " const current = ctx.session.ratesPage || 0\n"
+ " const allKeys = Object.keys(ctx.index)\n"
+ " // klskdlskakdsl\n"
+ " switch (ctx.match[1]) {\n"
+ " case 'prev':\n"
+ " ctx.session.ratesPage = current > 0\n"
+ " ? current - 1 // slklklkl\n"
+ " : 0\n"
+ " break\n"
+ " case 'next':\n"
+ " ctx.session.ratesPage = current < (allKeys.length / PAGE_SIZE) - 1\n"
+ " ? current + 1\n"
+ " : (allKeys.length / PAGE_SIZE) - 1\n"
+ " break\n"
+ " default:\n"
+ " }\n\n"
+ " const { data } = await getRates(ctx.session.ratesPage * PAGE_SIZE, PAGE_SIZE)\n"
+ " .catch(debug)\n\n"
+ " await ctx.editMessageText(\n"
+ " data.map(smallTemplateMd).join(''),\n"
+ " {\n"
+ " disable_web_page_preview: true,\n"
+ " parse_mode: 'Markdown',\n"
+ " ...pagination('rates', ctx.session.ratesPage, allKeys.length),\n"
+ " }\n"
+ " ).catch(debug)\n\n"
+ " return ctx.answerCbQuery()\n"
+ "})\n\n"
+ "/**\n"
+ " * Handles noop actions\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "bot.action(/^/noop$/, async (ctx) => ctx.answerCbQuery())\n\n"
+ "/**\n"
+ " * Handles the help command\n"
+ " */\n"
+ "bot.command('help', async (ctx) => {\n"
+ " const message = await ctx.replyWithMarkdown(`\n"
+ "*Usage:*\n\n"
+ "\\`!list\\` - List of all supported currencies without rates\n"
+ "\\`!rates\\` - Paginated list of all supported currencies with rates\n"
+ "\\`!{TICKER}\\` - Show rate of exact currency by its ticker\n"
+ "`)\n\n"
+ " if (message) {\n"
+ " setTimeout(() => {\n"
+ " ctx.deleteMessage(message.message_id)\n"
+ " }, 7000)\n"
+ " }\n"
+ "})\n\n"
+ "// bot.command('leave', async (ctx) => {\n"
+ "// ctx.tg.leaveChat(ctx.chat.id)\n"
+ "// })\n\n"
+ "// bot.on('inline_query', async (ctx) => {\n\n"
+ "// })\n\n"
+ "/**\n"
+ " * Init the bot\n"
+ " *\n"
+ " * @param {TelegrafContext} ctx The bot's context\n"
+ " */\n"
+ "const run = async (instance) => {\n"
+ " const { data } = await getRates().catch(console.log)\n\n"
+ " instance.context.index = await mapCommands(data)\n"
+ " return instance\n"
+ "}\n\n"
+ "/**\n"
+ " * Start the bot\n"
+ " *\n"
+ " * @param {Telegraf} instance The bot instance\n"
+ " */\n"
+ "run(bot).then((instance) => {\n"
+ " instance.startPolling()\n"
+ "})";
final String subst = "";
final Pattern pattern = Pattern.compile(regex, Pattern.MULTILINE);
final Matcher matcher = pattern.matcher(string);
// The substituted value will be contained in the result variable
final String result = matcher.replaceAll(subst);
System.out.println("Substitution result: " + result);
}
}
Please keep in mind that these code samples are automatically generated and are not guaranteed to work. If you find any syntax errors, feel free to submit a bug report. For a full regex reference for Java, please visit: https://docs.oracle.com/javase/7/docs/api/java/util/regex/Pattern.html