Oracle
 sql >> डेटाबेस >  >> RDS >> Oracle

गतिविधि डेटा के आधार पर आईडी कॉलम बनाएं

मुझे लगता है कि यह चाल चलेगा:

WITH EVENTS AS (SELECT 'abc' usr, to_date('2016-01-01 08:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'login' event_type FROM dual UNION ALL
                SELECT 'abc' usr, to_date('2016-01-01 08:25:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'Stuff' event_type FROM dual UNION ALL
                SELECT 'abc' usr, to_date('2016-01-01 10:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'Stuff' event_type FROM dual UNION ALL
                SELECT 'abc' usr, to_date('2016-01-01 14:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'login' event_type FROM dual UNION ALL
                SELECT 'xyz' usr, to_date('2015-12-31 18:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'login' event_type FROM dual UNION ALL
                SELECT 'xyz' usr, to_date('2016-01-01 08:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'Logout' event_type FROM dual UNION ALL
                SELECT 'def' usr, to_date('2016-01-01 08:00:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'Logout' event_type FROM dual UNION ALL
                SELECT 'def' usr, to_date('2016-01-01 08:15:00', 'yyyy-mm-dd hh24:mi:ss') event_ts, 'Logout' event_type FROM dual)
SELECT usr,
       event_ts,
       event_type,
       SUM(counter) OVER (PARTITION BY usr ORDER BY event_ts) session_id
FROM   (SELECT usr,
               event_ts,
               event_type,
               CASE WHEN LAG(event_type, 1, 'Logout') OVER (PARTITION BY usr ORDER BY event_ts) = 'Logout' THEN 1
                    WHEN event_type = 'Logout' THEN 0
                    WHEN event_ts - LAG(event_ts) OVER (PARTITION BY usr ORDER BY event_ts) > 1/24 THEN 1
                    WHEN event_type = 'login' THEN 1
                    ELSE 0
               END counter
        FROM   EVENTS);

USR EVENT_TS            EVENT_TYPE SESSION_ID
--- ------------------- ---------- ----------
abc 2016-01-01 08:00:00 login               1
abc 2016-01-01 08:25:00 Stuff               1
abc 2016-01-01 10:00:00 Stuff               2
abc 2016-01-01 14:00:00 login               3
def 2016-01-01 08:00:00 Logout              1
def 2016-01-01 08:15:00 Logout              2
xyz 2015-12-31 18:00:00 login               1
xyz 2016-01-01 08:00:00 Logout              1

यह समाधान तर्क-शॉर्ट सर्किटिंग पर निर्भर करता है जो CASE अभिव्यक्ति में होता है और यह तथ्य कि event_type शून्य नहीं है। यह भी मानता है कि एक पंक्ति में एकाधिक लॉगआउट को अलग सत्रों के रूप में गिना जाता है:

  1. यदि पिछली पंक्ति एक लॉगआउट पंक्ति थी (और यदि कोई पिछली पंक्ति नहीं है - यानी सेट में पहली पंक्ति के लिए - इसे लॉगआउट पंक्ति के रूप में मानें), तो हम काउंटर को एक से बढ़ाना चाहते हैं। (लॉगआउट सत्र को समाप्त करते हैं, इसलिए लॉगआउट के बाद हमारे पास हमेशा एक नया सत्र होता है।)
  2. यदि वर्तमान पंक्ति लॉगआउट है, तो यह मौजूदा सत्र को समाप्त कर देता है। इसलिए, काउंटर को नहीं बढ़ाया जाना चाहिए।
  3. यदि वर्तमान पंक्ति का समय पिछली पंक्ति से एक घंटे से अधिक है, तो काउंटर को एक से बढ़ा दें।
  4. यदि वर्तमान पंक्ति एक लॉगिन पंक्ति है, तो यह एक नया सत्र है, इसलिए काउंटर को एक से बढ़ा दें।
  5. किसी अन्य मामले के लिए, हम काउंटर नहीं बढ़ाते हैं।

एक बार जब हम ऐसा कर लेते हैं, तो यह काउंटर पर कुल रन बनाने की बात है।



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Oracle में SQL क्वेरी ट्यूनिंग

  2. EF और TransactionScope SQL सर्वर और Oracle दोनों के लिए DTC में वृद्धि/फैले हुए बिना?

  3. अमान्य रिलेशनल ऑपरेटर

  4. Oracle प्रपत्र ऐप से POST डेटा पढ़ें

  5. इंटरनेट एक्सप्लोरर 8 में ओरेकल फॉर्म/एप्लिकेशन JInitator का उपयोग कर रहे हैं