v5: прямые ссылки на источник в каждой новости

This commit is contained in:
Ilyas_Dussenov 2026-06-01 05:24:53 +00:00
parent 055a2a3043
commit 52ce2be489

View File

@ -60,10 +60,10 @@ body{font:15px/1.6 -apple-system,BlinkMacSystemFont,"Segoe UI",Inter,system-ui,s
.feed-title a:hover{color:var(--cyan);text-decoration:underline} .feed-title a:hover{color:var(--cyan);text-decoration:underline}
.feed-meta a.src-link{color:var(--blue);text-decoration:none;font-size:12px} .feed-meta a.src-link{color:var(--blue);text-decoration:none;font-size:12px}
.feed-meta a.src-link:hover{text-decoration:underline} .feed-meta a.src-link:hover{text-decoration:underline}
.feed-item.clickable{cursor:pointer;transition:background .15s;border-radius:8px;margin:0 -8px;padding:12px 8px} .feed-item[data-href],.tl-item[data-href]{cursor:pointer;transition:background .15s;border-radius:8px;margin:0 -8px;padding:12px 8px}
.feed-item.clickable:hover{background:rgba(0,229,255,.04)} .feed-item[data-href]:hover,.tl-item[data-href]:hover{background:rgba(0,229,255,.04)}
.tl-item.clickable{cursor:pointer;transition:background .15s;border-radius:8px;margin:0 -8px;padding:14px 8px} .src-search-link{color:var(--cyan);text-decoration:none;font-size:12px;font-weight:600;margin-left:8px;white-space:nowrap}
.tl-item.clickable:hover{background:rgba(0,229,255,.04)} .src-search-link:hover{text-decoration:underline}
.tl-text a{color:var(--text);text-decoration:none} .tl-text a{color:var(--text);text-decoration:none}
.tl-text a:hover{color:var(--cyan);text-decoration:underline} .tl-text a:hover{color:var(--cyan);text-decoration:underline}
.source-card-link{text-decoration:none;color:inherit;display:block;transition:border-color .15s,transform .15s} .source-card-link{text-decoration:none;color:inherit;display:block;transition:border-color .15s,transform .15s}
@ -285,14 +285,14 @@ const COMPANIES = [
const CATEGORIES = ['Экономика','Социальная сфера','Трудовые споры','Экология','Инфраструктура','Кадровые назначения','Финансы','Производство','Транспорт','Безопасность']; const CATEGORIES = ['Экономика','Социальная сфера','Трудовые споры','Экология','Инфраструктура','Кадровые назначения','Финансы','Производство','Транспорт','Безопасность'];
const NEWS_SOURCES = [ const NEWS_SOURCES = [
{name:'Tengrinews',type:'news',url:'https://tengrinews.kz'}, {name:'Tengrinews',type:'news',url:'https://tengrinews.kz',searchPattern:'https://tengrinews.kz/search/?q={q}'},
{name:'Zakon.kz',type:'news',url:'https://www.zakon.kz'}, {name:'Zakon.kz',type:'news',url:'https://www.zakon.kz',searchPattern:'https://www.zakon.kz/search/?q={q}'},
{name:'Informburo',type:'news',url:'https://informburo.kz'}, {name:'Informburo',type:'news',url:'https://informburo.kz',searchPattern:'https://informburo.kz/search?query={q}'},
{name:'Kapital.kz',type:'news',url:'https://kapital.kz'}, {name:'Kapital.kz',type:'news',url:'https://kapital.kz',searchPattern:'https://kapital.kz/search/?q={q}'},
{name:'Forbes Kazakhstan',type:'news',url:'https://forbes.kz'}, {name:'Forbes Kazakhstan',type:'news',url:'https://forbes.kz',searchPattern:'https://forbes.kz/search/?q={q}'},
{name:'Orda.kz',type:'news',url:'https://orda.kz'}, {name:'Orda.kz',type:'news',url:'https://orda.kz',searchPattern:'https://orda.kz/?s={q}'},
{name:'DKnews',type:'news',url:'https://dknews.kz'}, {name:'DKnews',type:'news',url:'https://dknews.kz',searchPattern:'https://dknews.kz/?s={q}'},
{name:'Baigenews',type:'news',url:'https://baigenews.kz'} {name:'Baigenews',type:'news',url:'https://baigenews.kz',searchPattern:'https://baigenews.kz/?s={q}'}
]; ];
const SOCIAL_SOURCES = [ const SOCIAL_SOURCES = [
@ -303,9 +303,9 @@ const SOCIAL_SOURCES = [
]; ];
const GOV_SOURCES = [ const GOV_SOURCES = [
{name:'Самрук-Казына (оф. сайт)',type:'gov',url:'https://sk.kz'}, {name:'Самрук-Казына (оф. сайт)',type:'gov',url:'https://sk.kz',searchPattern:'https://sk.kz/search/?q={q}'},
{name:'KASE (биржа)',type:'gov',url:'https://kase.kz'}, {name:'KASE (биржа)',type:'gov',url:'https://kase.kz',searchPattern:'https://kase.kz/ru/news/?q={q}'},
{name:'Правительство РК',type:'gov',url:'https://www.gov.kz'}, {name:'Правительство РК',type:'gov',url:'https://www.gov.kz',searchPattern:'https://www.gov.kz/search?q={q}'},
{name:'Минэнерго РК',type:'gov',url:'https://www.gov.kz/memleket/entities/energo'}, {name:'Минэнерго РК',type:'gov',url:'https://www.gov.kz/memleket/entities/energo'},
{name:'Минтранс РК',type:'gov',url:'https://www.gov.kz/memleket/entities/transport'}, {name:'Минтранс РК',type:'gov',url:'https://www.gov.kz/memleket/entities/transport'},
{name:'Агентство по финмониторингу',type:'gov',url:'https://www.gov.kz/memleket/entities/afm'} {name:'Агентство по финмониторингу',type:'gov',url:'https://www.gov.kz/memleket/entities/afm'}
@ -379,18 +379,25 @@ function typeLabel(type){
return'Прочее'; return'Прочее';
} }
function srcSearchUrl(source,company){
const q=encodeURIComponent(company||'Самрук-Казына');
if(source.searchPattern) return source.searchPattern.replace('{q}',q);
return 'https://www.google.com/search?q=site%3A'+new URL(source.url).hostname.replace('www.','')+'+'+q;
}
function renderAll(){ function renderAll(){
const feed=generateFeed(6); const feed=generateFeed(6);
document.getElementById('feedList').innerHTML=feed.map(f=>{ document.getElementById('feedList').innerHTML=feed.map(f=>{
const q=encodeURIComponent(f.company||'Самрук-Казына'); const q=encodeURIComponent(f.company||'Самрук-Казына');
const searchUrl='https://news.google.com/search?q='+q+'&hl=ru'; const searchUrl='https://news.google.com/search?q='+q+'&hl=ru';
const srcUrl=f.source.url||('https://news.google.com/search?q='+encodeURIComponent(f.source.name+' '+f.company)+'&hl=ru'); const srcUrl=f.source.url||('https://news.google.com/search?q='+encodeURIComponent(f.source.name+' '+f.company)+'&hl=ru');
const srcSearch=srcSearchUrl(f.source,f.company);
return ` return `
<div class="feed-item clickable" data-href="${searchUrl}"> <div class="feed-item" data-href="${searchUrl}">
<div class="feed-source ${srcClass(f.type)}">${srcIcon(f.type)}</div> <div class="feed-source ${srcClass(f.type)}">${srcIcon(f.type)}</div>
<div class="feed-info"> <div class="feed-info">
<div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div> <div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div>
<div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span></div> <div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span><a href="${srcSearch}" target="_blank" class="src-search-link" title="Искать на сайте источника">↗ источник</a></div>
</div> </div>
</div>`}).join(''); </div>`}).join('');
@ -398,13 +405,15 @@ function renderAll(){
document.getElementById('timelineList').innerHTML=tl.map(f=>{ document.getElementById('timelineList').innerHTML=tl.map(f=>{
const q=encodeURIComponent(f.company||'Самрук-Казына'); const q=encodeURIComponent(f.company||'Самрук-Казына');
const searchUrl='https://news.google.com/search?q='+q+'&hl=ru'; const searchUrl='https://news.google.com/search?q='+q+'&hl=ru';
const srcSearch=srcSearchUrl(f.source,f.company);
return ` return `
<div class="tl-item clickable" data-href="${searchUrl}"> <div class="tl-item" data-href="${searchUrl}">
<span class="tl-time">${f.time}</span> <span class="tl-time">${f.time}</span>
<span class="tl-dot ${priorityDot(f.priority)}"></span> <span class="tl-dot ${priorityDot(f.priority)}"></span>
<div class="tl-content"> <div class="tl-content">
<div class="tl-text"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div> <div class="tl-text"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div>
<span class="tl-tag ${typeTag(f.type)}">${typeLabel(f.type)}</span> <span class="tl-tag ${typeTag(f.type)}">${typeLabel(f.type)}</span>
<a href="${srcSearch}" target="_blank" class="src-search-link" title="Искать на сайте источника">↗ ${f.source.name}</a>
</div> </div>
</div>`}).join(''); </div>`}).join('');
@ -434,12 +443,13 @@ function renderAll(){
const q=encodeURIComponent(f.company||'Самрук-Казына'); const q=encodeURIComponent(f.company||'Самрук-Казына');
const searchUrl='https://news.google.com/search?q='+q+'&hl=ru'; const searchUrl='https://news.google.com/search?q='+q+'&hl=ru';
const srcUrl=f.source.url||'#'; const srcUrl=f.source.url||'#';
const srcSearch=srcSearchUrl(f.source,f.company);
return ` return `
<div class="feed-item clickable" data-href="${searchUrl}"> <div class="feed-item" data-href="${searchUrl}">
<div class="feed-source src-news">📰</div> <div class="feed-source src-news">📰</div>
<div class="feed-info"> <div class="feed-info">
<div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div> <div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div>
<div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span></div> <div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span><a href="${srcSearch}" target="_blank" class="src-search-link" title="Искать на сайте источника">↗ источник</a></div>
</div> </div>
</div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>'; </div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>';
@ -448,12 +458,13 @@ function renderAll(){
const q=encodeURIComponent(f.company||'Самрук-Казына'); const q=encodeURIComponent(f.company||'Самрук-Казына');
const searchUrl='https://news.google.com/search?q='+q+'&hl=ru'; const searchUrl='https://news.google.com/search?q='+q+'&hl=ru';
const srcUrl=f.source.url||'#'; const srcUrl=f.source.url||'#';
const srcSearch=srcSearchUrl(f.source,f.company);
return ` return `
<div class="feed-item clickable" data-href="${searchUrl}"> <div class="feed-item" data-href="${searchUrl}">
<div class="feed-source src-social">💬</div> <div class="feed-source src-social">💬</div>
<div class="feed-info"> <div class="feed-info">
<div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div> <div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div>
<div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span></div> <div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span><a href="${srcSearch}" target="_blank" class="src-search-link" title="Искать на сайте источника">↗ источник</a></div>
</div> </div>
</div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>'; </div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>';
@ -462,12 +473,13 @@ function renderAll(){
const q=encodeURIComponent(f.company||'Самрук-Казына'); const q=encodeURIComponent(f.company||'Самрук-Казына');
const searchUrl='https://news.google.com/search?q='+q+'&hl=ru'; const searchUrl='https://news.google.com/search?q='+q+'&hl=ru';
const srcUrl=f.source.url||'#'; const srcUrl=f.source.url||'#';
const srcSearch=srcSearchUrl(f.source,f.company);
return ` return `
<div class="feed-item clickable" data-href="${searchUrl}"> <div class="feed-item" data-href="${searchUrl}">
<div class="feed-source src-gov">🏛</div> <div class="feed-source src-gov">🏛</div>
<div class="feed-info"> <div class="feed-info">
<div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div> <div class="feed-title"><a href="${searchUrl}" target="_blank" title="Искать в Google News">${f.text}</a></div>
<div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span></div> <div class="feed-meta"><a href="${srcUrl}" target="_blank" class="src-link" title="Перейти к источнику">${f.source.name}</a><span>${f.time}</span><span>${f.category}</span><a href="${srcSearch}" target="_blank" class="src-search-link" title="Искать на сайте источника">↗ источник</a></div>
</div> </div>
</div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>'; </div>`}).join(''):'<div class="empty"><div class="empty-icon">📭</div>Нет данных</div>';
@ -512,7 +524,7 @@ setInterval(()=>{updateClock();},1000);
setInterval(()=>{renderAll();},30000); setInterval(()=>{renderAll();},30000);
document.addEventListener('click',function(e){ document.addEventListener('click',function(e){
const row=e.target.closest('.clickable[data-href]'); const row=e.target.closest('[data-href]');
if(row&&e.target.tagName!=='A'){ if(row&&e.target.tagName!=='A'){
window.open(row.dataset.href,'_blank'); window.open(row.dataset.href,'_blank');
} }